This source file includes following definitions.
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
- SEC
   1 
   2 
   3 
   4 
   5 
   6 
   7 
   8 
   9 #include <stddef.h>
  10 #include <string.h>
  11 #include <arpa/inet.h>
  12 #include <linux/bpf.h>
  13 #include <linux/if_ether.h>
  14 #include <linux/if_packet.h>
  15 #include <linux/ip.h>
  16 #include <linux/ipv6.h>
  17 #include <linux/types.h>
  18 #include <linux/tcp.h>
  19 #include <linux/socket.h>
  20 #include <linux/pkt_cls.h>
  21 #include <linux/erspan.h>
  22 #include "bpf_helpers.h"
  23 #include "bpf_endian.h"
  24 
  25 #define ERROR(ret) do {\
  26                 char fmt[] = "ERROR line:%d ret:%d\n";\
  27                 bpf_trace_printk(fmt, sizeof(fmt), __LINE__, ret); \
  28         } while (0)
  29 
  30 int _version SEC("version") = 1;
  31 
  32 struct geneve_opt {
  33         __be16  opt_class;
  34         __u8    type;
  35         __u8    length:5;
  36         __u8    r3:1;
  37         __u8    r2:1;
  38         __u8    r1:1;
  39         __u8    opt_data[8]; 
  40 };
  41 
  42 struct vxlan_metadata {
  43         __u32     gbp;
  44 };
  45 
  46 SEC("gre_set_tunnel")
  47 int _gre_set_tunnel(struct __sk_buff *skb)
  48 {
  49         int ret;
  50         struct bpf_tunnel_key key;
  51 
  52         __builtin_memset(&key, 0x0, sizeof(key));
  53         key.remote_ipv4 = 0xac100164; 
  54         key.tunnel_id = 2;
  55         key.tunnel_tos = 0;
  56         key.tunnel_ttl = 64;
  57 
  58         ret = bpf_skb_set_tunnel_key(skb, &key, sizeof(key),
  59                                      BPF_F_ZERO_CSUM_TX | BPF_F_SEQ_NUMBER);
  60         if (ret < 0) {
  61                 ERROR(ret);
  62                 return TC_ACT_SHOT;
  63         }
  64 
  65         return TC_ACT_OK;
  66 }
  67 
  68 SEC("gre_get_tunnel")
  69 int _gre_get_tunnel(struct __sk_buff *skb)
  70 {
  71         int ret;
  72         struct bpf_tunnel_key key;
  73         char fmt[] = "key %d remote ip 0x%x\n";
  74 
  75         ret = bpf_skb_get_tunnel_key(skb, &key, sizeof(key), 0);
  76         if (ret < 0) {
  77                 ERROR(ret);
  78                 return TC_ACT_SHOT;
  79         }
  80 
  81         bpf_trace_printk(fmt, sizeof(fmt), key.tunnel_id, key.remote_ipv4);
  82         return TC_ACT_OK;
  83 }
  84 
  85 SEC("ip6gretap_set_tunnel")
  86 int _ip6gretap_set_tunnel(struct __sk_buff *skb)
  87 {
  88         struct bpf_tunnel_key key;
  89         int ret;
  90 
  91         __builtin_memset(&key, 0x0, sizeof(key));
  92         key.remote_ipv6[3] = bpf_htonl(0x11); 
  93         key.tunnel_id = 2;
  94         key.tunnel_tos = 0;
  95         key.tunnel_ttl = 64;
  96         key.tunnel_label = 0xabcde;
  97 
  98         ret = bpf_skb_set_tunnel_key(skb, &key, sizeof(key),
  99                                      BPF_F_TUNINFO_IPV6 | BPF_F_ZERO_CSUM_TX |
 100                                      BPF_F_SEQ_NUMBER);
 101         if (ret < 0) {
 102                 ERROR(ret);
 103                 return TC_ACT_SHOT;
 104         }
 105 
 106         return TC_ACT_OK;
 107 }
 108 
 109 SEC("ip6gretap_get_tunnel")
 110 int _ip6gretap_get_tunnel(struct __sk_buff *skb)
 111 {
 112         char fmt[] = "key %d remote ip6 ::%x label %x\n";
 113         struct bpf_tunnel_key key;
 114         int ret;
 115 
 116         ret = bpf_skb_get_tunnel_key(skb, &key, sizeof(key),
 117                                      BPF_F_TUNINFO_IPV6);
 118         if (ret < 0) {
 119                 ERROR(ret);
 120                 return TC_ACT_SHOT;
 121         }
 122 
 123         bpf_trace_printk(fmt, sizeof(fmt),
 124                          key.tunnel_id, key.remote_ipv6[3], key.tunnel_label);
 125 
 126         return TC_ACT_OK;
 127 }
 128 
 129 SEC("erspan_set_tunnel")
 130 int _erspan_set_tunnel(struct __sk_buff *skb)
 131 {
 132         struct bpf_tunnel_key key;
 133         struct erspan_metadata md;
 134         int ret;
 135 
 136         __builtin_memset(&key, 0x0, sizeof(key));
 137         key.remote_ipv4 = 0xac100164; 
 138         key.tunnel_id = 2;
 139         key.tunnel_tos = 0;
 140         key.tunnel_ttl = 64;
 141 
 142         ret = bpf_skb_set_tunnel_key(skb, &key, sizeof(key),
 143                                      BPF_F_ZERO_CSUM_TX);
 144         if (ret < 0) {
 145                 ERROR(ret);
 146                 return TC_ACT_SHOT;
 147         }
 148 
 149         __builtin_memset(&md, 0, sizeof(md));
 150 #ifdef ERSPAN_V1
 151         md.version = 1;
 152         md.u.index = bpf_htonl(123);
 153 #else
 154         __u8 direction = 1;
 155         __u8 hwid = 7;
 156 
 157         md.version = 2;
 158         md.u.md2.dir = direction;
 159         md.u.md2.hwid = hwid & 0xf;
 160         md.u.md2.hwid_upper = (hwid >> 4) & 0x3;
 161 #endif
 162 
 163         ret = bpf_skb_set_tunnel_opt(skb, &md, sizeof(md));
 164         if (ret < 0) {
 165                 ERROR(ret);
 166                 return TC_ACT_SHOT;
 167         }
 168 
 169         return TC_ACT_OK;
 170 }
 171 
 172 SEC("erspan_get_tunnel")
 173 int _erspan_get_tunnel(struct __sk_buff *skb)
 174 {
 175         char fmt[] = "key %d remote ip 0x%x erspan version %d\n";
 176         struct bpf_tunnel_key key;
 177         struct erspan_metadata md;
 178         __u32 index;
 179         int ret;
 180 
 181         ret = bpf_skb_get_tunnel_key(skb, &key, sizeof(key), 0);
 182         if (ret < 0) {
 183                 ERROR(ret);
 184                 return TC_ACT_SHOT;
 185         }
 186 
 187         ret = bpf_skb_get_tunnel_opt(skb, &md, sizeof(md));
 188         if (ret < 0) {
 189                 ERROR(ret);
 190                 return TC_ACT_SHOT;
 191         }
 192 
 193         bpf_trace_printk(fmt, sizeof(fmt),
 194                         key.tunnel_id, key.remote_ipv4, md.version);
 195 
 196 #ifdef ERSPAN_V1
 197         char fmt2[] = "\tindex %x\n";
 198 
 199         index = bpf_ntohl(md.u.index);
 200         bpf_trace_printk(fmt2, sizeof(fmt2), index);
 201 #else
 202         char fmt2[] = "\tdirection %d hwid %x timestamp %u\n";
 203 
 204         bpf_trace_printk(fmt2, sizeof(fmt2),
 205                          md.u.md2.dir,
 206                          (md.u.md2.hwid_upper << 4) + md.u.md2.hwid,
 207                          bpf_ntohl(md.u.md2.timestamp));
 208 #endif
 209 
 210         return TC_ACT_OK;
 211 }
 212 
 213 SEC("ip4ip6erspan_set_tunnel")
 214 int _ip4ip6erspan_set_tunnel(struct __sk_buff *skb)
 215 {
 216         struct bpf_tunnel_key key;
 217         struct erspan_metadata md;
 218         int ret;
 219 
 220         __builtin_memset(&key, 0x0, sizeof(key));
 221         key.remote_ipv6[3] = bpf_htonl(0x11);
 222         key.tunnel_id = 2;
 223         key.tunnel_tos = 0;
 224         key.tunnel_ttl = 64;
 225 
 226         ret = bpf_skb_set_tunnel_key(skb, &key, sizeof(key),
 227                                      BPF_F_TUNINFO_IPV6);
 228         if (ret < 0) {
 229                 ERROR(ret);
 230                 return TC_ACT_SHOT;
 231         }
 232 
 233         __builtin_memset(&md, 0, sizeof(md));
 234 
 235 #ifdef ERSPAN_V1
 236         md.u.index = bpf_htonl(123);
 237         md.version = 1;
 238 #else
 239         __u8 direction = 0;
 240         __u8 hwid = 17;
 241 
 242         md.version = 2;
 243         md.u.md2.dir = direction;
 244         md.u.md2.hwid = hwid & 0xf;
 245         md.u.md2.hwid_upper = (hwid >> 4) & 0x3;
 246 #endif
 247 
 248         ret = bpf_skb_set_tunnel_opt(skb, &md, sizeof(md));
 249         if (ret < 0) {
 250                 ERROR(ret);
 251                 return TC_ACT_SHOT;
 252         }
 253 
 254         return TC_ACT_OK;
 255 }
 256 
 257 SEC("ip4ip6erspan_get_tunnel")
 258 int _ip4ip6erspan_get_tunnel(struct __sk_buff *skb)
 259 {
 260         char fmt[] = "ip6erspan get key %d remote ip6 ::%x erspan version %d\n";
 261         struct bpf_tunnel_key key;
 262         struct erspan_metadata md;
 263         __u32 index;
 264         int ret;
 265 
 266         ret = bpf_skb_get_tunnel_key(skb, &key, sizeof(key),
 267                                      BPF_F_TUNINFO_IPV6);
 268         if (ret < 0) {
 269                 ERROR(ret);
 270                 return TC_ACT_SHOT;
 271         }
 272 
 273         ret = bpf_skb_get_tunnel_opt(skb, &md, sizeof(md));
 274         if (ret < 0) {
 275                 ERROR(ret);
 276                 return TC_ACT_SHOT;
 277         }
 278 
 279         bpf_trace_printk(fmt, sizeof(fmt),
 280                         key.tunnel_id, key.remote_ipv4, md.version);
 281 
 282 #ifdef ERSPAN_V1
 283         char fmt2[] = "\tindex %x\n";
 284 
 285         index = bpf_ntohl(md.u.index);
 286         bpf_trace_printk(fmt2, sizeof(fmt2), index);
 287 #else
 288         char fmt2[] = "\tdirection %d hwid %x timestamp %u\n";
 289 
 290         bpf_trace_printk(fmt2, sizeof(fmt2),
 291                          md.u.md2.dir,
 292                          (md.u.md2.hwid_upper << 4) + md.u.md2.hwid,
 293                          bpf_ntohl(md.u.md2.timestamp));
 294 #endif
 295 
 296         return TC_ACT_OK;
 297 }
 298 
 299 SEC("vxlan_set_tunnel")
 300 int _vxlan_set_tunnel(struct __sk_buff *skb)
 301 {
 302         int ret;
 303         struct bpf_tunnel_key key;
 304         struct vxlan_metadata md;
 305 
 306         __builtin_memset(&key, 0x0, sizeof(key));
 307         key.remote_ipv4 = 0xac100164; 
 308         key.tunnel_id = 2;
 309         key.tunnel_tos = 0;
 310         key.tunnel_ttl = 64;
 311 
 312         ret = bpf_skb_set_tunnel_key(skb, &key, sizeof(key),
 313                                      BPF_F_ZERO_CSUM_TX);
 314         if (ret < 0) {
 315                 ERROR(ret);
 316                 return TC_ACT_SHOT;
 317         }
 318 
 319         md.gbp = 0x800FF; 
 320         ret = bpf_skb_set_tunnel_opt(skb, &md, sizeof(md));
 321         if (ret < 0) {
 322                 ERROR(ret);
 323                 return TC_ACT_SHOT;
 324         }
 325 
 326         return TC_ACT_OK;
 327 }
 328 
 329 SEC("vxlan_get_tunnel")
 330 int _vxlan_get_tunnel(struct __sk_buff *skb)
 331 {
 332         int ret;
 333         struct bpf_tunnel_key key;
 334         struct vxlan_metadata md;
 335         char fmt[] = "key %d remote ip 0x%x vxlan gbp 0x%x\n";
 336 
 337         ret = bpf_skb_get_tunnel_key(skb, &key, sizeof(key), 0);
 338         if (ret < 0) {
 339                 ERROR(ret);
 340                 return TC_ACT_SHOT;
 341         }
 342 
 343         ret = bpf_skb_get_tunnel_opt(skb, &md, sizeof(md));
 344         if (ret < 0) {
 345                 ERROR(ret);
 346                 return TC_ACT_SHOT;
 347         }
 348 
 349         bpf_trace_printk(fmt, sizeof(fmt),
 350                         key.tunnel_id, key.remote_ipv4, md.gbp);
 351 
 352         return TC_ACT_OK;
 353 }
 354 
 355 SEC("ip6vxlan_set_tunnel")
 356 int _ip6vxlan_set_tunnel(struct __sk_buff *skb)
 357 {
 358         struct bpf_tunnel_key key;
 359         int ret;
 360 
 361         __builtin_memset(&key, 0x0, sizeof(key));
 362         key.remote_ipv6[3] = bpf_htonl(0x11); 
 363         key.tunnel_id = 22;
 364         key.tunnel_tos = 0;
 365         key.tunnel_ttl = 64;
 366 
 367         ret = bpf_skb_set_tunnel_key(skb, &key, sizeof(key),
 368                                      BPF_F_TUNINFO_IPV6);
 369         if (ret < 0) {
 370                 ERROR(ret);
 371                 return TC_ACT_SHOT;
 372         }
 373 
 374         return TC_ACT_OK;
 375 }
 376 
 377 SEC("ip6vxlan_get_tunnel")
 378 int _ip6vxlan_get_tunnel(struct __sk_buff *skb)
 379 {
 380         char fmt[] = "key %d remote ip6 ::%x label %x\n";
 381         struct bpf_tunnel_key key;
 382         int ret;
 383 
 384         ret = bpf_skb_get_tunnel_key(skb, &key, sizeof(key),
 385                                      BPF_F_TUNINFO_IPV6);
 386         if (ret < 0) {
 387                 ERROR(ret);
 388                 return TC_ACT_SHOT;
 389         }
 390 
 391         bpf_trace_printk(fmt, sizeof(fmt),
 392                          key.tunnel_id, key.remote_ipv6[3], key.tunnel_label);
 393 
 394         return TC_ACT_OK;
 395 }
 396 
 397 SEC("geneve_set_tunnel")
 398 int _geneve_set_tunnel(struct __sk_buff *skb)
 399 {
 400         int ret, ret2;
 401         struct bpf_tunnel_key key;
 402         struct geneve_opt gopt;
 403 
 404         __builtin_memset(&key, 0x0, sizeof(key));
 405         key.remote_ipv4 = 0xac100164; 
 406         key.tunnel_id = 2;
 407         key.tunnel_tos = 0;
 408         key.tunnel_ttl = 64;
 409 
 410         __builtin_memset(&gopt, 0x0, sizeof(gopt));
 411         gopt.opt_class = bpf_htons(0x102); 
 412         gopt.type = 0x08;
 413         gopt.r1 = 0;
 414         gopt.r2 = 0;
 415         gopt.r3 = 0;
 416         gopt.length = 2; 
 417         *(int *) &gopt.opt_data = bpf_htonl(0xdeadbeef);
 418 
 419         ret = bpf_skb_set_tunnel_key(skb, &key, sizeof(key),
 420                                      BPF_F_ZERO_CSUM_TX);
 421         if (ret < 0) {
 422                 ERROR(ret);
 423                 return TC_ACT_SHOT;
 424         }
 425 
 426         ret = bpf_skb_set_tunnel_opt(skb, &gopt, sizeof(gopt));
 427         if (ret < 0) {
 428                 ERROR(ret);
 429                 return TC_ACT_SHOT;
 430         }
 431 
 432         return TC_ACT_OK;
 433 }
 434 
 435 SEC("geneve_get_tunnel")
 436 int _geneve_get_tunnel(struct __sk_buff *skb)
 437 {
 438         int ret;
 439         struct bpf_tunnel_key key;
 440         struct geneve_opt gopt;
 441         char fmt[] = "key %d remote ip 0x%x geneve class 0x%x\n";
 442 
 443         ret = bpf_skb_get_tunnel_key(skb, &key, sizeof(key), 0);
 444         if (ret < 0) {
 445                 ERROR(ret);
 446                 return TC_ACT_SHOT;
 447         }
 448 
 449         ret = bpf_skb_get_tunnel_opt(skb, &gopt, sizeof(gopt));
 450         if (ret < 0) {
 451                 ERROR(ret);
 452                 return TC_ACT_SHOT;
 453         }
 454 
 455         bpf_trace_printk(fmt, sizeof(fmt),
 456                         key.tunnel_id, key.remote_ipv4, gopt.opt_class);
 457         return TC_ACT_OK;
 458 }
 459 
 460 SEC("ip6geneve_set_tunnel")
 461 int _ip6geneve_set_tunnel(struct __sk_buff *skb)
 462 {
 463         struct bpf_tunnel_key key;
 464         struct geneve_opt gopt;
 465         int ret;
 466 
 467         __builtin_memset(&key, 0x0, sizeof(key));
 468         key.remote_ipv6[3] = bpf_htonl(0x11); 
 469         key.tunnel_id = 22;
 470         key.tunnel_tos = 0;
 471         key.tunnel_ttl = 64;
 472 
 473         ret = bpf_skb_set_tunnel_key(skb, &key, sizeof(key),
 474                                      BPF_F_TUNINFO_IPV6);
 475         if (ret < 0) {
 476                 ERROR(ret);
 477                 return TC_ACT_SHOT;
 478         }
 479 
 480         __builtin_memset(&gopt, 0x0, sizeof(gopt));
 481         gopt.opt_class = bpf_htons(0x102); 
 482         gopt.type = 0x08;
 483         gopt.r1 = 0;
 484         gopt.r2 = 0;
 485         gopt.r3 = 0;
 486         gopt.length = 2; 
 487         *(int *) &gopt.opt_data = bpf_htonl(0xfeedbeef);
 488 
 489         ret = bpf_skb_set_tunnel_opt(skb, &gopt, sizeof(gopt));
 490         if (ret < 0) {
 491                 ERROR(ret);
 492                 return TC_ACT_SHOT;
 493         }
 494 
 495         return TC_ACT_OK;
 496 }
 497 
 498 SEC("ip6geneve_get_tunnel")
 499 int _ip6geneve_get_tunnel(struct __sk_buff *skb)
 500 {
 501         char fmt[] = "key %d remote ip 0x%x geneve class 0x%x\n";
 502         struct bpf_tunnel_key key;
 503         struct geneve_opt gopt;
 504         int ret;
 505 
 506         ret = bpf_skb_get_tunnel_key(skb, &key, sizeof(key),
 507                                      BPF_F_TUNINFO_IPV6);
 508         if (ret < 0) {
 509                 ERROR(ret);
 510                 return TC_ACT_SHOT;
 511         }
 512 
 513         ret = bpf_skb_get_tunnel_opt(skb, &gopt, sizeof(gopt));
 514         if (ret < 0) {
 515                 ERROR(ret);
 516                 return TC_ACT_SHOT;
 517         }
 518 
 519         bpf_trace_printk(fmt, sizeof(fmt),
 520                         key.tunnel_id, key.remote_ipv4, gopt.opt_class);
 521 
 522         return TC_ACT_OK;
 523 }
 524 
 525 SEC("ipip_set_tunnel")
 526 int _ipip_set_tunnel(struct __sk_buff *skb)
 527 {
 528         struct bpf_tunnel_key key = {};
 529         void *data = (void *)(long)skb->data;
 530         struct iphdr *iph = data;
 531         struct tcphdr *tcp = data + sizeof(*iph);
 532         void *data_end = (void *)(long)skb->data_end;
 533         int ret;
 534 
 535         
 536         if (data + sizeof(*iph) + sizeof(*tcp) > data_end) {
 537                 ERROR(1);
 538                 return TC_ACT_SHOT;
 539         }
 540 
 541         key.tunnel_ttl = 64;
 542         if (iph->protocol == IPPROTO_ICMP) {
 543                 key.remote_ipv4 = 0xac100164; 
 544         } else {
 545                 if (iph->protocol != IPPROTO_TCP || iph->ihl != 5)
 546                         return TC_ACT_SHOT;
 547 
 548                 if (tcp->dest == bpf_htons(5200))
 549                         key.remote_ipv4 = 0xac100164; 
 550                 else if (tcp->dest == bpf_htons(5201))
 551                         key.remote_ipv4 = 0xac100165; 
 552                 else
 553                         return TC_ACT_SHOT;
 554         }
 555 
 556         ret = bpf_skb_set_tunnel_key(skb, &key, sizeof(key), 0);
 557         if (ret < 0) {
 558                 ERROR(ret);
 559                 return TC_ACT_SHOT;
 560         }
 561 
 562         return TC_ACT_OK;
 563 }
 564 
 565 SEC("ipip_get_tunnel")
 566 int _ipip_get_tunnel(struct __sk_buff *skb)
 567 {
 568         int ret;
 569         struct bpf_tunnel_key key;
 570         char fmt[] = "remote ip 0x%x\n";
 571 
 572         ret = bpf_skb_get_tunnel_key(skb, &key, sizeof(key), 0);
 573         if (ret < 0) {
 574                 ERROR(ret);
 575                 return TC_ACT_SHOT;
 576         }
 577 
 578         bpf_trace_printk(fmt, sizeof(fmt), key.remote_ipv4);
 579         return TC_ACT_OK;
 580 }
 581 
 582 SEC("ipip6_set_tunnel")
 583 int _ipip6_set_tunnel(struct __sk_buff *skb)
 584 {
 585         struct bpf_tunnel_key key = {};
 586         void *data = (void *)(long)skb->data;
 587         struct iphdr *iph = data;
 588         struct tcphdr *tcp = data + sizeof(*iph);
 589         void *data_end = (void *)(long)skb->data_end;
 590         int ret;
 591 
 592         
 593         if (data + sizeof(*iph) + sizeof(*tcp) > data_end) {
 594                 ERROR(1);
 595                 return TC_ACT_SHOT;
 596         }
 597 
 598         __builtin_memset(&key, 0x0, sizeof(key));
 599         key.remote_ipv6[3] = bpf_htonl(0x11); 
 600         key.tunnel_ttl = 64;
 601 
 602         ret = bpf_skb_set_tunnel_key(skb, &key, sizeof(key),
 603                                      BPF_F_TUNINFO_IPV6);
 604         if (ret < 0) {
 605                 ERROR(ret);
 606                 return TC_ACT_SHOT;
 607         }
 608 
 609         return TC_ACT_OK;
 610 }
 611 
 612 SEC("ipip6_get_tunnel")
 613 int _ipip6_get_tunnel(struct __sk_buff *skb)
 614 {
 615         int ret;
 616         struct bpf_tunnel_key key;
 617         char fmt[] = "remote ip6 %x::%x\n";
 618 
 619         ret = bpf_skb_get_tunnel_key(skb, &key, sizeof(key),
 620                                      BPF_F_TUNINFO_IPV6);
 621         if (ret < 0) {
 622                 ERROR(ret);
 623                 return TC_ACT_SHOT;
 624         }
 625 
 626         bpf_trace_printk(fmt, sizeof(fmt), bpf_htonl(key.remote_ipv6[0]),
 627                          bpf_htonl(key.remote_ipv6[3]));
 628         return TC_ACT_OK;
 629 }
 630 
 631 SEC("ip6ip6_set_tunnel")
 632 int _ip6ip6_set_tunnel(struct __sk_buff *skb)
 633 {
 634         struct bpf_tunnel_key key = {};
 635         void *data = (void *)(long)skb->data;
 636         struct ipv6hdr *iph = data;
 637         struct tcphdr *tcp = data + sizeof(*iph);
 638         void *data_end = (void *)(long)skb->data_end;
 639         int ret;
 640 
 641         
 642         if (data + sizeof(*iph) + sizeof(*tcp) > data_end) {
 643                 ERROR(1);
 644                 return TC_ACT_SHOT;
 645         }
 646 
 647         key.remote_ipv6[0] = bpf_htonl(0x2401db00);
 648         key.tunnel_ttl = 64;
 649 
 650         if (iph->nexthdr == 58 ) {
 651                 key.remote_ipv6[3] = bpf_htonl(1);
 652         } else {
 653                 if (iph->nexthdr != 6 ) {
 654                         ERROR(iph->nexthdr);
 655                         return TC_ACT_SHOT;
 656                 }
 657 
 658                 if (tcp->dest == bpf_htons(5200)) {
 659                         key.remote_ipv6[3] = bpf_htonl(1);
 660                 } else if (tcp->dest == bpf_htons(5201)) {
 661                         key.remote_ipv6[3] = bpf_htonl(2);
 662                 } else {
 663                         ERROR(tcp->dest);
 664                         return TC_ACT_SHOT;
 665                 }
 666         }
 667 
 668         ret = bpf_skb_set_tunnel_key(skb, &key, sizeof(key),
 669                                      BPF_F_TUNINFO_IPV6);
 670         if (ret < 0) {
 671                 ERROR(ret);
 672                 return TC_ACT_SHOT;
 673         }
 674 
 675         return TC_ACT_OK;
 676 }
 677 
 678 SEC("ip6ip6_get_tunnel")
 679 int _ip6ip6_get_tunnel(struct __sk_buff *skb)
 680 {
 681         int ret;
 682         struct bpf_tunnel_key key;
 683         char fmt[] = "remote ip6 %x::%x\n";
 684 
 685         ret = bpf_skb_get_tunnel_key(skb, &key, sizeof(key),
 686                                      BPF_F_TUNINFO_IPV6);
 687         if (ret < 0) {
 688                 ERROR(ret);
 689                 return TC_ACT_SHOT;
 690         }
 691 
 692         bpf_trace_printk(fmt, sizeof(fmt), bpf_htonl(key.remote_ipv6[0]),
 693                          bpf_htonl(key.remote_ipv6[3]));
 694         return TC_ACT_OK;
 695 }
 696 
 697 SEC("xfrm_get_state")
 698 int _xfrm_get_state(struct __sk_buff *skb)
 699 {
 700         struct bpf_xfrm_state x;
 701         char fmt[] = "reqid %d spi 0x%x remote ip 0x%x\n";
 702         int ret;
 703 
 704         ret = bpf_skb_get_xfrm_state(skb, 0, &x, sizeof(x), 0);
 705         if (ret < 0)
 706                 return TC_ACT_OK;
 707 
 708         bpf_trace_printk(fmt, sizeof(fmt), x.reqid, bpf_ntohl(x.spi),
 709                          bpf_ntohl(x.remote_ipv4));
 710         return TC_ACT_OK;
 711 }
 712 
 713 char _license[] SEC("license") = "GPL";