Esempio n. 1
0
def bpf_hook_socket():
    # initialize BPF - load source code from http-parse-simple.c
    host_ip, host_port = bpf_tool.convert_host_addr(CONFIG.host_ip)
    params = {
        "HOST_IP": hex(host_ip or 0),
    }
    bpf_text = bpf_tool.load_bpf_prog(CONFIG.http_filter_ebpf, params)

    bpf = BPF(text=bpf_text, debug=0)
    # print(dir(bpf))
    # print(bpf.dump_func("my_filter"))

    #load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
    #more info about eBPF program types
    #http://man7.org/linux/man-pages/man2/bpf.2.html
    function_http_filter = bpf.load_func(CONFIG.http_ebpf_section,
                                         BPF.SOCKET_FILTER)
    bpf_tool.bpf_dump_func(bpf, CONFIG.http_ebpf_section,
                           CONFIG.http_filter_ebpf)

    #create raw socket, bind it to interface
    #attach bpf program to socket created
    BPF.attach_raw_socket(function_http_filter, CONFIG.net_interface)

    #get file descriptor of the socket previously created inside BPF.attach_raw_socket
    socket_fd = function_http_filter.sock

    #create python socket object, from the file descriptor
    sock = socket.fromfd(socket_fd, socket.PF_PACKET, socket.SOCK_RAW,
                         socket.IPPROTO_IP)
    #set it as blocking socket
    sock.setblocking(True)

    return bpf, socket_fd
    def run(self):
        # ENABLE THIS PART TO ENABLE SINGLE PACKET MONITOR - END (2/1)
        bpf_text = self.get_bpf_text_file(self.map_name)
        self._logger.debug(bpf_text)

        bpf = BPF(text=bpf_text)
        # bpf = BPF(src_file="flow_measure.c", cflags=["-w", "-DMAPNAME=%s" % map_name])
        function_skb_matching = bpf.load_func("flow_measure", BPF.SOCKET_FILTER)
        BPF.attach_raw_socket(function_skb_matching, self.networking_port)
        flow_cnt_table = bpf.get_table(self.map_name)  # retrieve packet_cnt map

        self._logger.info("Measurement Function {} was successfully loaded.".format(self.networking_port))

        try:
            while True:
                start_time = time.time()

                flow_tuples = flow_cnt_table.items()

                if len(flow_tuples) != 0:
                    flow_cnt_table.clear()

                    msgs = self.create_message(flow_tuples)
                    # self._logger.debug(msgs)

                    try:
                        producer = KafkaProducer(bootstrap_servers=[self.kafka_url])

                        _bucket = []
                        for msg in msgs:
                            _bucket.append(msg)
                            if len(_bucket) > 5000:
                                producer.send(self.kafka_topic, json.dumps(_bucket).encode('utf-8'))
                                self._logger.info("Measured Flows: {}".format(_bucket))
                                _bucket.clear()
                        if len(_bucket) > 0:
                            producer.send(self.kafka_topic, json.dumps(_bucket).encode('utf-8'))
                            self._logger.info("Measured Flows: {}".format(_bucket))
                            _bucket.clear()

                        producer.close()
                        self._logger.info("Send kafka message successfully")

                    except NoBrokersAvailable as noBrokerExt:
                        self._logger.error("Kafka Broker in Security Post is not accessible")

                end_time = time.time()
                next_sleep_interval = float(self.setting["output_interval"]) - (end_time - start_time)
                if next_sleep_interval > 0:
                    time.sleep(float(self.setting["output_interval"]))

        except KeyboardInterrupt:
            flow_cnt_table.clear()
            self._logger.warning("Keyboard Interrupted")
            exit()
Esempio n. 3
0
def load_ebpf_program():

    print("Loading program into Interface")
    mode = BPF.SOCKET_FILTER
    func_name = "colletor"

    #load eBPF program
    bpf = BPF(src_file="colletor.c", debug=8)

    #load function
    function = bpf.load_func(func_name, mode)

    #attach functino to network interface
    bpf.attach_raw_socket(function, interface)

    return bpf
Esempio n. 4
0
def loadFilter(program, function):
  # initialize BPF - load source code from filters/program.c
  bpf.append(BPF(src_file = "filters/"+program,debug = 0))

  #load eBPF program function of type SOCKET_FILTER into the kernel eBPF vm
  function_mail_filter.append(bpf[-1].load_func(function, BPF.SOCKET_FILTER))

  #create raw socket, bind it to interface
  #attach bpf program to socket created
  BPF.attach_raw_socket(function_mail_filter[-1], interface)

  #get file descriptor of the socket previously created inside BPF.attach_raw_socket
  socket_fd.append(function_mail_filter[-1].sock)

  #create python socket object, from the file descriptor
  sock.append(socket.fromfd(socket_fd[-1],socket.PF_PACKET,socket.SOCK_RAW,socket.IPPROTO_IP))

  #set it as blocking socket
  sock[-1].setblocking(True)

  return socket_fd[-1]
    def _init_bpf(self):
        # initialize BPF - load source code from http-parse-simple.c
        self._bpf_bytecode = BPF(src_file=self._bpf_file, debug=0)

        # load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
        # more info about eBPF program types http://man7.org/linux/man-pages/man2/bpf.2.html
        function_ip_filter = self._bpf_bytecode.load_func(
            self._bpf_func, BPF.SOCKET_FILTER)

        # create raw socket, bind it to eth0
        # attach bpf program to socket created
        BPF.attach_raw_socket(function_ip_filter, self._target_net_if)

        # get file descriptor of the socket previously created inside BPF.attach_raw_socket
        self._socket_fd = function_ip_filter.sock

        # create python socket object, from the file descriptor
        self._socket = socket.fromfd(self._socket_fd, socket.PF_PACKET,
                                     socket.SOCK_RAW, socket.IPPROTO_IP)

        # set it as blocking socket
        self._socket.setblocking(True)
if len(argv) > 3:
    usage()

print("binding socket to '%s'" % interface)

# initialize BPF - load source code from http-parse-simple.c
bpf = BPF(src_file="http-parse-simple.c", debug=0)

#load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
#more info about eBPF program types
#http://man7.org/linux/man-pages/man2/bpf.2.html
function_http_filter = bpf.load_func("http_filter", BPF.SOCKET_FILTER)

#create raw socket, bind it to interface
#attach bpf program to socket created
BPF.attach_raw_socket(function_http_filter, interface)

#get file descriptor of the socket previously created inside BPF.attach_raw_socket
socket_fd = function_http_filter.sock

#create python socket object, from the file descriptor
sock = socket.fromfd(socket_fd, socket.PF_PACKET, socket.SOCK_RAW,
                     socket.IPPROTO_IP)
#set it as blocking socket
sock.setblocking(True)

while 1:
    #retrieve raw packet from socket
    packet_str = os.read(socket_fd, 2048)

    #DEBUG - print raw packet in hex format
def print_skb_event(cpu, data, size):
    global tester_send

    class SkbEvent(ct.Structure):
        #        _fields_ = [ ("magic", ct.c_uint32),("magic2", ct.c_uint32)]
        _fields_ = [("magic", ct.c_uint32)]

    skb_event = ct.cast(data, ct.POINTER(SkbEvent)).contents


bpf = BPF(text=bpf_text)

function_skb_matching = bpf.load_func("packet_monitor", BPF.SOCKET_FILTER)

BPF.attach_raw_socket(function_skb_matching, INTERFACE)

bpf["skb_events"].open_perf_buffer(print_skb_event)

# retrieeve packet_cnt map
packet_cnt = bpf.get_table('packet_cnt')  # retrieeve packet_cnt map

#sys.stdout = open('myoutput.txt','w')


def decimal_to_human(input_value):
    input_value = int(input_value)
    hex_value = hex(input_value)[2:]
    pt3 = literal_eval((str('0x' + str(hex_value[-2:]))))
    pt2 = literal_eval((str('0x' + str(hex_value[-4:-2]))))
    pt1 = literal_eval((str('0x' + str(hex_value[-6:-4]))))
Esempio n. 8
0
import sys
import socket
import os

# initialize BPF - load source code from http-parse.c
bpf = BPF(src_file = "http-parse.c",debug = 0)

#load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
#more info about eBPF program types
#http://man7.org/linux/man-pages/man2/bpf.2.html
function_http_filter = bpf.load_func("http_filter", BPF.SOCKET_FILTER)

#create raw socket, bind it to eth0
#attach bpf program to socket created
BPF.attach_raw_socket(function_http_filter, "eth0")

#get file descriptor of the socket previously created inside BPF.attach_raw_socket
socket_fd = function_http_filter.sock

#create python socket object, from the file descriptor
sock = socket.fromfd(socket_fd,socket.PF_PACKET,socket.SOCK_RAW,socket.IPPROTO_IP)
#set it as blocking socket
sock.setblocking(True)

while 1:
  #retrieve raw packet from socket
  packet_str = os.read(socket_fd,2048)

  #DEBUG - print raw packet in hex format
  #packet_hex = toHex(packet_str)
Esempio n. 9
0
        if len(hv) == 1:
            hv = '0' + hv
        lst.append(hv)

    return reduce(lambda x, y:x + y, lst)

# initialize BPF - load source code from http-parse-simple.c
bpf = BPF(src_file="mcd_planes_tracing.c", debug=0)

# load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
# more info about eBPF program types http://man7.org/linux/man-pages/man2/bpf.2.html
function_ip_filter = bpf.load_func("ip_filter", BPF.SOCKET_FILTER)

# create raw socket, bind it to eth0
# attach bpf program to socket created
BPF.attach_raw_socket(function_ip_filter, "eno2")

ni.ifaddresses('eno2')
ip = ni.ifaddresses('eno2')[ni.AF_INET][0]['addr']

# get file descriptor of the socket previously created inside BPF.attach_raw_socket
socket_fd = function_ip_filter.sock

# create python socket object, from the file descriptor
sock = socket.fromfd(socket_fd, socket.PF_PACKET, socket.SOCK_RAW, socket.IPPROTO_IP)

# set it as blocking socket
sock.setblocking(True)

print("MachineIP Hostname   ipver     Src IP Addr          Dst IP Addr    src Port    Dst Port      protocol  TCP_Window_Size Packet_Length")
Esempio n. 10
0
if len(argv) > 5:
    usage()

print("binding socket to '%s'" % interface)

#initialize BPF - load source code from http-parse-simple.c
bpf = BPF(src_file="data-plane-tracing.c", debug=0)

#load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
#more info about eBPF program types http://man7.org/linux/man-pages/man2/bpf.2.html
function_vlan_filter = bpf.load_func("vlan_filter", BPF.SOCKET_FILTER)

#create raw socket, bind it to eth0
#attach bpf program to socket created
BPF.attach_raw_socket(function_vlan_filter, interface)

#get file descriptor of the socket previously created inside BPF.attach_raw_socket
socket_fd = function_vlan_filter.sock

#create python socket object, from the file descriptor
sock = socket.fromfd(socket_fd, socket.PF_PACKET, socket.SOCK_RAW,
                     socket.IPPROTO_IP)

#set it as blocking socket
sock.setblocking(True)

#get interface ip address. In case ip is not set then just add 127.0.0.1.
ni.ifaddresses(interface)
try:
    ip = ni.ifaddresses(interface)[ni.AF_INET][0]['addr']
Esempio n. 11
0
def main():
    """Main loop"""

    # Parse args
    parser = argparse.ArgumentParser(
        description='Append timestamps to all UDP packets received from SFC.',
        formatter_class=argparse.RawTextHelpFormatter
    )

    parser.add_argument('--in_ifce', help="Ingress interface.", default='eth1')
    parser.add_argument('--eg_ifce', help="Egress interface.", default='eth2')

    args = parser.parse_args()
    in_ifce = args.in_ifce
    eg_ifce = args.eg_ifce

    # --- Ingress Interface ---

    # Load BPF program, written in C code
    bpf = BPF(src_file="./udp_filter.c", debug=0)
    filter_func = bpf.load_func("udp_filter", BPF.SOCKET_FILTER)

    # Bind a new raw socket to the ingress interface
    BPF.attach_raw_socket(filter_func, in_ifce)
    print('[INFO] Attach eBPF raw socket to interface: %s' % in_ifce)

    recv_sock_fd = filter_func.sock
    recv_sock = socket.fromfd(recv_sock_fd, socket.AF_PACKET, socket.SOCK_RAW,
                              socket.htons(3))
    recv_sock.setblocking(True)

    # --- Egress Interface ---

    send_sock = socket.socket(
        socket.AF_PACKET, socket.SOCK_RAW, socket.htons(3))
    send_sock.bind((eg_ifce, 0))
    print('[INFO] Bind send socket to interface: %s' % eg_ifce)

    # --- Frame Processing ---

    eth_frame = bytearray(BUFFER_SIZE)

    # Recv loop
    # MARK: Looks same with my raw socket implementation in the DA
    print('[INFO] Enter main looping...')
    try:
        while True:
            # MARK: Use blocking IO
            frame_len = recv_sock.recv_into(eth_frame, BUFFER_SIZE)
            # Get time stamp in microseconds.
            recv_time_b = struct.pack('!Q', int(time.time() * 1e6))
            ts_len = len(recv_time_b)
            # Append time stamps
            hd_offset = 0
            hd_offset += ETH_HDL  # move to IP header
            # Check IP version and calc header length
            ver_ihl = struct.unpack('>B', eth_frame[hd_offset:hd_offset + 1])[0]
            ihl = 4 * int(hex(ver_ihl)[-1])
            # IP total length
            old_ip_tlen = struct.unpack(
                '>H', eth_frame[hd_offset + 2:hd_offset + 4])[0]
            hd_offset += ihl  # move to UDP header
            udp_pl_offset = hd_offset + UDP_HDL

            # UDP payload length
            old_udp_pl_len = struct.unpack(
                '>H', eth_frame[hd_offset + 4:hd_offset + 6]
            )[0] - UDP_HDL

            # Append recv time stamp at end
            eth_frame[udp_pl_offset + old_udp_pl_len:udp_pl_offset +
                      old_udp_pl_len + ts_len] = recv_time_b

            # Set UDP and IP total length with new payload
            new_udp_tlen = struct.pack(
                '>H', (old_udp_pl_len + UDP_HDL + ts_len),
            )
            eth_frame[hd_offset + 4:hd_offset + 6] = new_udp_tlen

            # MARK: Recalculate the UDP checksum
            #       Assume that the SRC_IP and DST_IP are always not modified by
            #       the SFC
            # TODO: Such information SHOULD provided by BPF
            # Get UDP pseudo header: src_ip, dst_ip, zero, protocol, udp_length
            # Set checksum to zero
            eth_frame[hd_offset + 6:hd_offset + 8] = struct.pack('>H', 0)
            # Create the pseudo UDP header
            pseudo_udp_header = struct.pack('!BBH', 0, socket.IPPROTO_UDP,
                                            old_udp_pl_len + ts_len + UDP_HDL)
            pseudo_udp_header = SRC_IP_B + DST_IP_B + pseudo_udp_header
            # src_port, dst_port, udp_length, 0
            udp_header = eth_frame[hd_offset:hd_offset + 8]
            udp_cksum = calc_udp_cksum(pseudo_udp_header+udp_header+eth_frame[
                udp_pl_offset:udp_pl_offset+old_udp_pl_len + ts_len])
            eth_frame[hd_offset + 6:hd_offset +
                      8] = struct.pack('>H', udp_cksum)

            # Move back to IP header
            hd_offset -= ihl
            new_ip_tlen = struct.pack(
                '>H', (old_ip_tlen + ts_len)
            )
            eth_frame[hd_offset + 2:hd_offset + 4] = new_ip_tlen

            # Set checksum field to zero
            eth_frame[hd_offset + 10:hd_offset + 12] = struct.pack('>H', 0)
            new_iph_cksum = calc_ih_cksum(
                eth_frame[hd_offset:hd_offset + ihl]
            )
            eth_frame[hd_offset + 10:hd_offset +
                      12] = struct.pack('<H', new_iph_cksum)
            frame_len += ts_len
            eth_frame[0:MAC_LEN] = DST_MAC_B
            eth_frame[MAC_LEN:MAC_LEN * 2] = SRC_MAC_B
            send_sock.send(eth_frame[0: frame_len])

    except KeyboardInterrupt:
        print("[INFO] KeyboardInterrupt detected, exits...")
        recv_sock.close()
        send_sock.close()
        sys.exit(0)
Esempio n. 12
0
def main():
    global interface_name

    arg1 = str(argv[1]) if 1 < len(argv) else None
    arg2 = str(argv[2]) if 2 < len(argv) else None
    no_args = (len(argv) == 1)
    one_arg = (len(argv) == 2)
    two_args = (len(argv) == 3)
    three_or_more_args = (len(argv) > 3)
    help_flag = (str(arg1) == "-h")
    interface_flag = (str(arg1) == "-i")

    if DEBUG_ARGS:
        print("arg1 = {}".format(arg1))
        print("arg2 = {}".format(arg2))
        print("no_args = {}".format(no_args))
        print("one_arg = {}".format(one_arg))
        print("two_args = {}".format(two_args))
        print("three_or_more_args = {}".format(three_or_more_args))
        print("help_flag = {}".format(help_flag))
        print("interface_flag = {}".format(interface_flag))

    if one_arg and help_flag:
        help()
        exit()

    if three_or_more_args or \
           (two_args and not interface_flag) or \
           (one_arg and not help_flag):
        usage()
        exit()

    if two_args and interface_flag:
        interface_name = argv[2]

    bpf = BPF(text=prog, debug=2)
    is_is_filter = bpf.load_func("isis_filter", BPF.SOCKET_FILTER)

    print("binding socket to '%s'" % interface_name)
    BPF.attach_raw_socket(is_is_filter, interface_name)

    # get file descriptor of the socket previously created inside BPF.attach_raw_socket
    socket_fd = is_is_filter.sock

    #create python socket object, from the file descriptor
    sock = socket.fromfd(socket_fd, socket.AF_PACKET, socket.SOCK_RAW, 0)
    sock.setblocking(True)

    print("Starting to listen on socket {} -  use CTRL-C to terminate. \n".
          format(interface_name))
    pcap_fp = open('data.pcapng', 'wb')

    shb_opts = [
        pcapng.option.ShbHardware("Dell"),
        pcapng.option.ShbOs("Ubuntu"),
        pcapng.option.ShbUserAppl("IntelliJ Idea")
    ]
    shb_obj = pcapng.block.SectionHeaderBlock(shb_opts)
    shb_packed_bytes = shb_obj.pack()
    pcap_fp.write(shb_packed_bytes)  # must be 1st block

    idb_opts = [
        pcapng.option.IdbName(interface_name),
        pcapng.option.IdbDescription("primary interface on host"),
        pcapng.option.IdbSpeed(12345)
    ]
    idb_obj = pcapng.block.InterfaceDescBlock(
        pcapng.linktype.LINKTYPE_ETHERNET, idb_opts)  # optional block
    pcap_fp.write(idb_obj.pack())

    count = 0
    while True:
        count += 1
        dummy, remainder = divmod(count, 100)
        if (remainder == 0):
            print('.', end='')
            sys.stdout.flush()
        if False:
            pkt_bytes = get_next_packet(socket_fd)
            dbg_print(pkt_bytes)
            pcap_fp.write(pcapng.block.SimplePacketBlock(pkt_bytes).pack())

        if True:
            pkt_bytes = get_next_packet(socket_fd)
            dbg_print(pkt_bytes)

            epb_opts = [
                pcapng.option.EpbFlags([13, 14, 15, 16]),
                pcapng.option.EpbHash('just about any hash spec can go here'),
                pcapng.option.EpbDropCount(13)
            ]
            pcap_fp.write(
                pcapng.block.EnhancedPacketBlock(0, pkt_bytes, len(pkt_bytes),
                                                 epb_opts).pack())
Esempio n. 13
0
            i += 1

    return (c_ubyte * size).from_buffer(b)


# initialize BPF - load source code from http-parse-simple.c
bpf = BPF(src_file="dns_matching.c", debug=0)
# print(bpf.dump_func("dns_test"))

#load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
#more info about eBPF program types
#http://man7.org/linux/man-pages/man2/bpf.2.html
function_dns_matching = bpf.load_func("dns_matching", BPF.SOCKET_FILTER)

#create raw socket, bind it to eth0
#attach bpf program to socket created
BPF.attach_raw_socket(function_dns_matching, "eth1")

# Get the table.
cache = bpf.get_table("cache")

# Create first entry for foo.bar
key = cache.Key()
key.p = encode_dns("foo.bar")

leaf = cache.Leaf()
leaf.p = (c_ubyte * 4).from_buffer(bytearray(4))
cache[key] = leaf

bpf.trace_print()
            hv = '0' + hv
        lst.append(hv)

    return reduce(lambda x, y: x + y, lst)


# initialize BPF - load source code from http-parse-simple.c
bpf = BPF(src_file="mcd_planes_tracing.c", debug=0)

# load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
# more info about eBPF program types http://man7.org/linux/man-pages/man2/bpf.2.html
function_vxlan_filter = bpf.load_func("vxlan_filter", BPF.SOCKET_FILTER)

# create raw socket, bind it to eth0
# attach bpf program to socket created
BPF.attach_raw_socket(function_vxlan_filter, "eno5")

ni.ifaddresses('eno2')
ip = ni.ifaddresses('eno2')[ni.AF_INET][0]['addr']

# get file descriptor of the socket previously created inside BPF.attach_raw_socket
socket_fd = function_vxlan_filter.sock

# create python socket object, from the file descriptor
sock = socket.fromfd(socket_fd, socket.PF_PACKET, socket.SOCK_RAW,
                     socket.IPPROTO_IP)

# set it as blocking socket
sock.setblocking(True)

print(
Esempio n. 15
0
if len(argv) > 5:
    usage()

print ("binding socket to '%s'" % interface)	
 
#initialize BPF - load source code from http-parse-simple.c
bpf = BPF(src_file = "data-plane-tracing.c", debug = 0)

#load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
#more info about eBPF program types http://man7.org/linux/man-pages/man2/bpf.2.html
function_vlan_filter = bpf.load_func("vlan_filter", BPF.SOCKET_FILTER)

#create raw socket, bind it to eth0
#attach bpf program to socket created
BPF.attach_raw_socket(function_vlan_filter, interface)

#get file descriptor of the socket previously created inside BPF.attach_raw_socket
socket_fd = function_vlan_filter.sock

#create python socket object, from the file descriptor
sock = socket.fromfd(socket_fd,socket.PF_PACKET,socket.SOCK_RAW,socket.IPPROTO_IP)

#set it as blocking socket
sock.setblocking(True)

#get interface ip address. In case ip is not set then just add 127.0.0.1.
ni.ifaddresses(interface)
try:
    ip = ni.ifaddresses(interface)[ni.AF_INET][0]['addr']
except:
    sh.setLevel(logging.INFO)
    _logger.addHandler(sh)
    
    fh = logging.FileHandler(filename="./flow_measure.log")
    fh.setFormatter(fm)
    fh.setLevel(logging.DEBUG)
    _logger.addHandler(fh)

    # ENABLE THIS PART TO ENABLE SINGLE PACKET MONITOR - END (2/1)
    bpf_text = get_bpf_text_file(map_name)
    _logger.debug(bpf_text)

    bpf = BPF(text=bpf_text)
    # bpf = BPF(src_file="flow_measure.c", cflags=["-w", "-DMAPNAME=%s" % map_name])
    function_skb_matching = bpf.load_func("flow_measure", BPF.SOCKET_FILTER)
    BPF.attach_raw_socket(function_skb_matching, networking_point)
    flow_cnt_table = bpf.get_table(map_name)  # retrieve packet_cnt map

    _logger.info("Measurement Function {} was successfully loaded.".format(function_name))

    try:
        while True:
            start_time = time.time()

            flow_tuples = flow_cnt_table.items()

            if len(flow_tuples) != 0:
                flow_cnt_table.clear()

                msg_dict = create_message(flow_tuples)
                msg_dict["point"] = "{}.{}".format(where, networking_point)
Esempio n. 17
0
    usage()

print("binding socket to '%s'" % interface)

# initialize BPF - load source code from mqtts_dumper.c
bpf = BPF(src_file="mqtts_dumper.c",
          cflags=["-DFILTER_PORT=" + str(filter_port)])

#load eBPF program mqtts_dumper of type SOCKET_FILTER into the kernel eBPF vm
#more info about eBPF program types
#http://man7.org/linux/man-pages/man2/bpf.2.html
function_mqtts_dumper = bpf.load_func("mqtts_dumper", BPF.SOCKET_FILTER)

#create raw socket, bind it to interface
#attach bpf program to socket created
BPF.attach_raw_socket(function_mqtts_dumper, interface)

#get file descriptor of the socket previously created inside BPF.attach_raw_socket
socket_fd = function_mqtts_dumper.sock

#create python socket object, from the file descriptor
sock = socket.fromfd(socket_fd, socket.PF_PACKET, socket.SOCK_RAW,
                     socket.IPPROTO_IP)
#set it as blocking socket
sock.setblocking(True)

while True:
    #retrieve raw packet from socket
    packet_bytes = os.read(socket_fd, 2048)

    print('PKTPKTs')
Esempio n. 18
0
 def setUp(self):
     b = BPF(arg1, arg2, debug=0)
     fn = b.load_func("on_packet", BPF.SOCKET_FILTER)
     BPF.attach_raw_socket(fn, "eth0")
     self.stats = b.get_table("stats", Key, Leaf)
Esempio n. 19
0
  return (c_ubyte * size).from_buffer(b)



# initialize BPF - load source code from http-parse-simple.c
bpf = BPF(src_file = "dns_matching.c", debug=0)
# print(bpf.dump_func("dns_test"))

#load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
#more info about eBPF program types
#http://man7.org/linux/man-pages/man2/bpf.2.html
function_dns_matching = bpf.load_func("dns_matching", BPF.SOCKET_FILTER)


#create raw socket, bind it to eth0
#attach bpf program to socket created
BPF.attach_raw_socket(function_dns_matching, "eth1")

# Get the table.
cache = bpf.get_table("cache")

# Create first entry for foo.bar
key = cache.Key()
key.p = encode_dns("foo.bar")

leaf = cache.Leaf()
leaf.p = (c_ubyte * 4).from_buffer(bytearray(4))
cache[key] = leaf

bpf.trace_print()
Esempio n. 20
0
if len(argv) > 3:
  usage()

print ("binding socket to '%s'" % interface)

# initialize BPF - load source code from http-parse-simple.c
bpf = BPF(src_file = "http-parse-simple.c",debug = 0)

#load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
#more info about eBPF program types
#http://man7.org/linux/man-pages/man2/bpf.2.html
function_http_filter = bpf.load_func("http_filter", BPF.SOCKET_FILTER)

#create raw socket, bind it to interface
#attach bpf program to socket created
BPF.attach_raw_socket(function_http_filter, interface)

#get file descriptor of the socket previously created inside BPF.attach_raw_socket
socket_fd = function_http_filter.sock

#create python socket object, from the file descriptor
sock = socket.fromfd(socket_fd,socket.PF_PACKET,socket.SOCK_RAW,socket.IPPROTO_IP)
#set it as blocking socket
sock.setblocking(True)

while 1:
  #retrieve raw packet from socket
  packet_str = os.read(socket_fd,2048)

  #DEBUG - print raw packet in hex format
  #packet_hex = toHex(packet_str)
        lst.append(hv)

    return reduce(lambda x, y: x + y, lst)


# initialize BPF - load source code from http-parse-simple.c
bpf = BPF(src_file="packet_tracing.c", debug=0)

#load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
#more info about eBPF program types
#http://man7.org/linux/man-pages/man2/bpf.2.html
function_http_filter = bpf.load_func("http_filter", BPF.SOCKET_FILTER)

#create raw socket, bind it to eth0
#attach bpf program to socket created
BPF.attach_raw_socket(function_http_filter, "enp0s25")

ni.ifaddresses('enp0s25')
ip = ''
#ip = ni.ifaddresses('ens2f2')[ni.AF_INET][0]['addr']

#get file descriptor of the socket previously created inside BPF.attach_raw_socket
socket_fd = function_http_filter.sock

#create python socket object, from the file descriptor
sock = socket.fromfd(socket_fd, socket.PF_PACKET, socket.SOCK_RAW,
                     socket.IPPROTO_IP)
#set it as blocking socket
sock.setblocking(True)
print(
    "MachineIP   ipver     Src IP Addr     src Port     Dst IP Addr    Dst Port  Packet Length   protocol  Local_Src_Addr  Local_des_Addr  VNI VLANID  "
Esempio n. 22
0
    help='List of domain names separated by space. For example: -d abc.def xyz.mno')
args = parser.parse_args()

# initialize BPF - load source code from http-parse-simple.c
bpf = BPF(src_file = "dns_matching.c", debug=0)
# print(bpf.dump_func("dns_test"))

#load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
#more info about eBPF program types
#http://man7.org/linux/man-pages/man2/bpf.2.html
function_dns_matching = bpf.load_func("dns_matching", BPF.SOCKET_FILTER)


#create raw socket, bind it to user provided interface
#attach bpf program to socket created
BPF.attach_raw_socket(function_dns_matching, args.interface)

# Get the table.
cache = bpf.get_table("cache")

# Add cache entries
for e in args.domains:
  print(">>>> Adding map entry: ", e)
  add_cache_entry(cache, e)

print("\nTry to lookup some domain names using nslookup from another terminal.")
print("For example:  nslookup foo.bar")
print("\nBPF program will filter-in DNS packets which match with map entries.")
print("Packets received by user space program will be printed here")
print("\nHit Ctrl+C to end...")
Esempio n. 23
0
 def setUp(self):
     b = BPF(arg1, arg2, debug=0)
     fn = b.load_func("on_packet", BPF.SOCKET_FILTER)
     BPF.attach_raw_socket(fn, "eth0")
     self.stats = b.get_table("stats", Key, Leaf)
Esempio n. 24
0
    data.pid = bpf_get_current_pid_tgid();
    data.ts = bpf_ktime_get_ns();
    bpf_get_current_comm(&data.comm, sizeof(data.comm));

    events.perf_submit(ctx, &data, sizeof(data));

    return 0;
}
"""

# load BPF program
b = BPF(text=prog)
#b.attach_kprobe(event=b.get_syscall_fnname("clone"), fn_name="hello")

function_skb = b.load_func("hello", BPF.SOCKET_FILTER)
BPF.attach_raw_socket(function_skb, INTERFACE)

# header
print("%-18s %-16s %-6s %s" % ("TIME(s)", "COMM", "PID", "MESSAGE"))

# process event
start = 0


def print_event(cpu, data, size):
    global start
    event = b["events"].event(data)
    if start == 0:
        start = event.ts
    time_s = (float(event.ts - start)) / 1000000000
    printb(b"%-18.9f %-16s %-6d %s" %
Esempio n. 25
0
# can't exceed BPF_HASH() size
if len(args.target_uri) > 128:
  print("%s: error: too many arguments" % parser.prog)
  parser.print_help()
  sys.exit(-1)

# initialize BPF - load source code from ebpf_ttl.c
bpf = BPF(src_file="ebpf_ttl.c", debug=0)

#load eBPF program synack_ttl of type SOCKET_FILTER into the kernel eBPF vm
function_synack_ttl = bpf.load_func("synack_ttl", BPF.SOCKET_FILTER)

#create raw socket, bind it to interface
#attach bpf program to socket created
BPF.attach_raw_socket(function_synack_ttl, interface)

# Get the table.
ttlmap = bpf.get_table("ttlmap")

# Add cache entries
for t in args.target_uri:
  print(">>>> Adding map entry: ", t)
  add_ttlmap_entry(ttlmap, t)

socket.setdefaulttimeout(1)  
for t in args.target_uri:
  addr, port, af = parse_dst(t)
  s = socket.socket(af, socket.SOCK_STREAM)
  s.connect((addr, port))
  
Esempio n. 26
0
if len(argv) == 3:
  if str(argv[1]) == '-i':
    interface = argv[2]
  else:
    usage()

if len(argv) > 3:
  usage()

# initialize BPF - load source code from http-parse-simple.c
bpf = BPF(src_file = "dns_record.c", debug=0)
# load bpf -- it's a socket filter
f_dns = bpf.load_func("dns_record", BPF.SOCKET_FILTER)
# create a raw socket on eth0 and attach our bpf
BPF.attach_raw_socket(f_dns, interface)


# bytecode_str = bpf.dump_func("dns_record")
# print(":".join("{:02x}".format(ord(c)) for c in bytecode_str))

# # dump the BPF program
# bpf.dump_func("dns_record")



# Create first entry for foo.bar
# key = cache.Key()
# key.p = encode_dns("foo.bar")
# leaf = cache.Leaf()
# leaf.p = (c_ubyte * 4).from_buffer(bytearray(4))
Esempio n. 27
0
    help=
    'List of domain names separated by space. For example: -d abc.def xyz.mno')
args = parser.parse_args()

# initialize BPF - load source code from http-parse-simple.c
bpf = BPF(src_file="dns_matching.c", debug=0)
# print(bpf.dump_func("dns_test"))

#load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
#more info about eBPF program types
#http://man7.org/linux/man-pages/man2/bpf.2.html
function_dns_matching = bpf.load_func("dns_matching", BPF.SOCKET_FILTER)

#create raw socket, bind it to user provided interface
#attach bpf program to socket created
BPF.attach_raw_socket(function_dns_matching, args.interface)

# Get the table.
cache = bpf.get_table("cache")

# Add cache entries
for e in args.domains:
    print(">>>> Adding map entry: ", e)
    add_cache_entry(cache, e)

print(
    "\nTry to lookup some domain names using nslookup from another terminal.")
print("For example:  nslookup foo.bar")
print("\nBPF program will filter-in DNS packets which match with map entries.")
print("Packets received by user space program will be printed here")
print("\nHit Ctrl+C to end...")
Esempio n. 28
0
    return 

#-----FUNCTIONS-END-------------------------#


# initialize BPF - load source code from http-parse-complete.c
bpf = BPF(src_file = "http-parse-complete.c",debug = 0)

#load eBPF program http_filter of type SOCKET_FILTER into the kernel eBPF vm
#more info about eBPF program types
#http://man7.org/linux/man-pages/man2/bpf.2.html
function_http_filter = bpf.load_func("http_filter", BPF.SOCKET_FILTER)

#create raw socket, bind it to eth0
#attach bpf program to socket created
BPF.attach_raw_socket(function_http_filter, "eth0")

#get file descriptor of the socket previously created inside BPF.attach_raw_socket
socket_fd = function_http_filter.sock

#create python socket object, from the file descriptor
sock = socket.fromfd(socket_fd,socket.PF_PACKET,socket.SOCK_RAW,socket.IPPROTO_IP)
#set it as blocking socket
sock.setblocking(True)

#get pointer to bpf map of type hash
bpf_sessions = bpf.get_table("sessions")

#packets counter
packet_count = 0
Esempio n. 29
0
def bpf_handler():
    global current_connection

    #arguments
    interface = "eth0"

    if len(argv) == 2:
        if str(argv[1]) == '-h':
            help()
        else:
            usage()

    if len(argv) == 3:
        if str(argv[1]) == '-i':
            interface = argv[2]
        else:
            usage()

    if len(argv) > 3:
        usage()

    success_text = open("./success", "rb").read()

    print("binding socket to '%s'" % interface)

    # initialize BPF - load source code from parse.c
    bpf = BPF(src_file="parse.c", debug=0)

    #load eBPF program filter of type SOCKET_FILTER into the kernel eBPF vm
    #more info about eBPF program types
    #http://man7.org/linux/man-pages/man2/bpf.2.html
    logging.info('JIT eBPF Code')
    function_filter = bpf.load_func("filter", BPF.SOCKET_FILTER)

    #create raw socket, bind it to interface
    #attach bpf program to socket created
    logging.info('Creating Raw Socket')
    BPF.attach_raw_socket(function_filter, interface)

    #get file descriptor of the socket previously created inside BPF.attach_raw_socket
    socket_fd = function_filter.sock

    #create python socket object, from the file descriptor
    sock = socket.fromfd(socket_fd, socket.PF_PACKET, socket.SOCK_RAW,
                         socket.IPPROTO_IP)
    #set it as blocking socket
    sock.setblocking(True)

    while True:
        #retrieve raw packet from socket
        packet_str = os.read(socket_fd, 2048)
        packet_bytearray = bytearray(packet_str)

        # Parse RAW data using scapy.. super general and easy
        c = Ether(packet_bytearray)
        if c.haslayer(IP):
            layer_ip = c.getlayer(IP)
            logging.info('IP: {} said the magic word ;-)'.format(layer_ip.src))
            if len(current_connection) > 0:
                for con, addr in current_connection:
                    if (layer_ip.src, layer_ip.sport) == addr:
                        con.send(success_text)
                logging.info('Sending success text now to: {}'.format(
                    layer_ip.src))