Add example for BPF+tc rate limiting

* Adding an example to address #59, simulation of bandwidth sharing

Signed-off-by: Brenden Blanco <bblanco@plumgrid.com>
diff --git a/examples/tc_neighbor_sharing.c b/examples/tc_neighbor_sharing.c
new file mode 100644
index 0000000..6ba7d35
--- /dev/null
+++ b/examples/tc_neighbor_sharing.c
@@ -0,0 +1,61 @@
+// Copyright (c) PLUMgrid, Inc.
+// Licensed under the Apache License, Version 2.0 (the "License")
+
+#include <bcc/proto.h>
+
+struct ipkey {
+  u32 client_ip;
+};
+
+BPF_TABLE("hash", struct ipkey, int, learned_ips, 1024);
+
+// trivial action
+int pass(struct __sk_buff *skb) {
+  return 1;
+}
+
+// Process each wan packet, and determine if the packet is in the IP
+// table or not. Learned IPs are rate-limited and unclassified are not.
+// returns: > 0 when an IP is known
+//          = 0 when an IP is not known, or non-IP traffic
+int classify_wan(struct __sk_buff *skb) {
+  BEGIN(ethernet);
+  PROTO(ethernet) {
+    switch (ethernet->type) {
+      case 0x0800: goto ip;
+    }
+    goto EOP;
+  }
+  PROTO(ip) {
+    u32 dip = ip->dst;
+    struct ipkey key = {.client_ip=dip};
+    int *val = learned_ips.lookup(&key);
+    if (val)
+      return *val;
+    goto EOP;
+  }
+EOP:
+  return 0;
+}
+
+// Process each neighbor packet, and store the source IP in the learned table.
+// Mark the inserted entry with a non-zero value to be used by the classify_wan
+// lookup.
+int classify_neighbor(struct __sk_buff *skb) {
+  BEGIN(ethernet);
+  PROTO(ethernet) {
+    switch (ethernet->type) {
+      case 0x0800: goto ip;
+    }
+    goto EOP;
+  }
+  PROTO(ip) {
+    u32 sip = ip->src;
+    struct ipkey key = {.client_ip=sip};
+    int val = 1;
+    learned_ips.lookup_or_init(&key, &val);
+    goto EOP;
+  }
+EOP:
+  return 1;
+}