杰瑞科技汇

Python Scapy在Linux中如何抓包分析?

Of course! Using Python with Scapy on Linux is a powerful combination for network analysis, security testing, and development. This guide will walk you through everything you need to know, from installation to practical examples.

Python Scapy在Linux中如何抓包分析?-图1
(图片来源网络,侵删)

Table of Contents

  1. What is Scapy? (A quick overview)
  2. Installation on Linux
  3. Essential Prerequisites
  4. Your First Scapy Script (The "Hello, World!" of Networking)
  5. Core Scapy Concepts
  6. Practical Examples
    • Example 1: Network Scanning (ARP Discovery)
    • Example 2: Crafting and Sending a Custom Packet (ICMP Echo Request)
    • Example 3: Sniffing Packets
  7. Crucial: Running Scapy with sudo
  8. Common Pitfalls and Best Practices
  9. Further Resources

What is Scapy?

Scapy is a Python interactive program that allows you to send, sniff, dissect, and forge network packets. This means you can:

  • Create packets from scratch (e.g., a TCP packet with specific flags).
  • Send packets and receive responses.
  • Sniff live network traffic.
  • Dissect packets to understand their contents.
  • Forge complex attacks or tools for network testing.

Unlike tools like hping3 or nmap, which are often single-purpose, Scapy is a toolkit. You build your own tools by combining different packet layers.


Installation on Linux

The easiest and most recommended way to install Scapy on a modern Linux distribution (like Ubuntu, Debian, Fedora, or Arch) is using pip.

Update your system's package list:

Python Scapy在Linux中如何抓包分析?-图2
(图片来源网络,侵删)
sudo apt update   # For Debian/Ubuntu
# or
sudo dnf update   # For Fedora/CentOS

Install Python and Pip (if not already installed):

sudo apt install python3 python3-pip   # For Debian/Ubuntu
# or
sudo dnf install python3 python3-pip   # For Fedora/CentOS

Install Scapy:

pip3 install scapy

This will install Scapy and its core dependencies.


Essential Prerequisites

For Scapy to work fully, especially for sniffing and sending packets at the raw socket level, you need specific Linux capabilities.

Python Scapy在Linux中如何抓包分析?-图3
(图片来源网络,侵删)
  • sudo access: You need root privileges to open raw sockets.
  • libpcap and tcpdump: These are fundamental for packet sniffing. Most likely, they are already installed or can be easily installed.
    sudo apt install libpcap-dev tcpdump   # For Debian/Ubuntu
    # or
    sudo dnf install libpcap tcpdump      # For Fedora/CentOS

Your First Scapy Script (The "Hello, World!" of Networking)

Let's create a simple script that sends an ICMP Echo Request (the kind of packet ping sends) and waits for a reply.

  1. Create a file named ping_sweep.py:

    nano ping_sweep.py
  2. Add the following code:

    from scapy.all import sr, IP, ICMP
    # The target IP address you want to ping
    target_ip = "8.8.8.8"
    # Create the packet
    # IP() layer sets the destination IP
    # ICMP() layer creates the ICMP Echo Request
    packet = IP(dst=target_ip)/ICMP()
    # Send the packet and wait for a response
    # sr() sends and receives packets.
    # It returns two lists: answered packets and unanswered packets.
    ans, unans = sr(packet, timeout=5, verbose=0)
    # Process the answered packets
    for sent_packet, received_packet in ans:
        # sent_packet is the packet we sent
        # received_packet is the packet we got back
        if received_packet.haslayer(ICMP):
            print(f"Received ICMP reply from {target_ip}")
            # You can inspect the layers like this:
            # print(received_packet.summary())
  3. Run the script (remember, sudo is required!):

    sudo python3 ping_sweep.py

If your network connection is working, you should see: Received ICMP reply from 8.8.8.8


Core Scapy Concepts

  • Packet: In Scapy, a network packet is an object. You build these objects by stacking layers.

    # A simple TCP packet
    tcp_packet = IP(dst="192.168.1.1") / TCP(dport=80, sport=12345)
  • Layers: These are the different parts of a packet (Ethernet, IP, TCP, ICMP, DNS, etc.). You import them from scapy.all.

    from scapy.all import Ether, IP, TCP, ICMP
  • Stacking: The operator is used to stack layers. Scapy is smart enough to handle the layering (e.g., it knows an IP packet must go inside an Ethernet frame if you're on a local network).

    # An Ethernet frame containing an IP packet containing a TCP packet
    eth_packet = Ether(dst="aa:bb:cc:dd:ee:ff") / IP(dst="192.168.1.1") / TCP(dport=443)
  • Sending:

    • send(): Sends packets at layer 2 (Data Link). Doesn't wait for a reply. Good for broadcasts.
    • sr(): Sends and receives packets at layer 3 (Network). Waits for answers. Returns a list of tuples (sent_packet, received_packet).
    • srp(): Sends and receives packets at layer 2 (Data Link). Waits for answers.
  • Sniffing:

    • sniff(): Captures live packets from the network.
    • You can use a prn (print packet) function to process each captured packet.
    • Use filter to apply BPF (Berkeley Packet Filter) syntax to only capture specific traffic (e.g., "tcp port 80").

Practical Examples

Example 1: Network Scanning (ARP Discovery)

This script discovers live hosts on your local network by sending ARP requests.

# arp_scan.py
from scapy.all import srp, Ether, ARP, conf
# Get the network interface and its IP
iface = conf.iface
ip = conf.iface.ip
# Scapy's get_if_addr() is more reliable
ip = get_if_addr(iface)
# Calculate the network range
# A simple way: get the first three octets and change the last to .1/24
network = '.'.join(ip.split('.')[:-1]) + '.1/24'
print(f"Scanning network: {network} on interface {iface}")
# Create the ARP packet to ask "who-has" a specific IP
# We'll let Scapy handle the range with the 'iface' parameter
arp_request = ARP(pdst=network)
# Create an Ethernet broadcast frame
ether = Ether(dst="ff:ff:ff:ff:ff:ff")
# Stack them
packet = ether / arp_request
# Send and receive at layer 2
# srp() sends and receives packets at layer 2
ans, unans = srp(packet, timeout=2, iface=iface, verbose=0)
print("Available devices in the network:")
print("IP" + " "*18 + "MAC")
print("-----------------------------------")
for sent, received in ans:
    # The response packet contains the MAC address
    mac = received[1].src
    ip = received[1].psrc
    print(f"{ip:<20}{mac}")

Run with sudo python3 arp_scan.py.

Example 2: Crafting and Sending a Custom Packet (ICMP Echo Request)

This is a more interactive version of our first example. It sends a single packet and prints a summary of the response.

# custom_ping.py
from scapy.all import sr, IP, ICMP
target_ip = input("Enter the target IP to ping: ")
# Create the packet
packet = IP(dst=target_ip)/ICMP()
print(f"\nSending ICMP Echo Request to {target_ip}...")
# Send and receive, timeout after 5 seconds
ans, unans = sr(packet, timeout=5, verbose=0)
if ans:
    for sent_pkt, recv_pkt in ans:
        print("\n--- Packet Summary ---")
        print("SENT PACKET:")
        print(sent_pkt.summary())
        print("\nRECEIVED PACKET:")
        print(recv_pkt.summary())
else:
    print(f"No response received from {target_ip}.")

Run with sudo python3 custom_ping.py.

Example 3: Sniffing Packets

This script sniffs for 10 ICMP packets and prints a summary of each one.

# icmp_sniffer.py
from scapy.all import sniff
# This function is called for each packet
def process_packet(packet):
    # We only care about ICMP packets
    if packet.haslayer(ICMP):
        print("\n--- Captured ICMP Packet ---")
        # Print a summary of the packet
        print(packet.summary())
print("Starting ICMP packet sniffer for 10 packets...")
print("Press Ctrl+C to stop early.")
# Sniff 10 packets and pass each one to process_packet
sniff(filter="icmp", prn=process_packet, count=10)
print("Sniffing finished.")

Run with sudo python3 icmp_sniffer.py. Now, open another terminal and ping google.com. You'll see the ICMP echo requests and replies captured by your script.


Crucial: Running Scapy with sudo

This cannot be overstated. Scapy requires root privileges to create and send raw packets.

  • Why? Normal user applications are not allowed to directly access the network hardware (network cards). This is a security feature of the Linux kernel. Only the root user can open a "raw socket" to build packets from scratch.
  • How? Always prefix your command with sudo:
    sudo python3 your_script.py
  • Security Warning: Running scripts as root is a security risk. Only run scripts from trusted sources. Be careful what you do with root access.

Common Pitfalls and Best Practices

  • sudo is mandatory: If you get Permission denied or Operation not permitted, you forgot sudo.
  • Verbose Mode: Use verbose=0 in sr(), send(), etc., to suppress Scapy's default output. Use verbose=1 or verbose=2 for more details when debugging.
  • Timeouts: Always set a timeout when sending packets. Otherwise, your script might hang indefinitely if a host is down or unresponsive.
  • Firewalls: Your local firewall or a remote host's firewall can block your packets, leading to "unanswered" results. This is normal behavior.
  • Use Interactive Mode: For quick testing and learning, use Scapy's interactive console:
    sudo scapy

    This gives you a Python shell with all Scapy objects pre-loaded. It's fantastic for experimenting.


Further Resources

分享:
扫描分享到社交APP
上一篇
下一篇