从入门到入土:[SEED-Lab]- Packet Sniffing and Spoofing Lab|嗅探与欺骗实验|详细说明|实验步骤|实验截图

本文主要是介绍从入门到入土:[SEED-Lab]- Packet Sniffing and Spoofing Lab|嗅探与欺骗实验|详细说明|实验步骤|实验截图,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

此博客仅用于记录个人学习进度,学识浅薄,若有错误观点欢迎评论区指出。欢迎各位前来交流。(部分材料来源网络,若有侵权,立即删除)
本人博客所有文章纯属学习之用,不涉及商业利益。不合适引用,自当删除!
若被用于非法行为,与我本人无关

[SEED-Lab]-Packet Sniffing and Spoofing Lab

  • 实验环境
  • PDF文件
  • 实验步骤
    • 环境配置
      • Labsetup
    • 操作步骤
      • Lab Task Set 1: Using Scapy to Sniff and Spoof Packets
        • Task 1.1: Sniffing Packets
          • task1.1A
          • task1.1B
        • Task 1.2: Spoofing ICMP Packets
        • Task 1.3: Traceroute
        • Task 1.4: Sniffing and-then Spoofing
        • Task 2.1
          • Task 2.1A: Understanding How a Sniffer Works
          • Task 2.1B: Writing Filters
          • Task2.1C: Sniffing Passwords
        • Task 2.2
          • Task 2.2A: Write a spoofing program
          • Task 2.2B: Spoof an ICMP Echo Request
        • Task 2.3: Sniff and then Spoof

实验环境

  • seed-ubuntu 20.04

PDF文件

  • 嗅探与欺骗实验

实验步骤

环境配置

Labsetup

传送门

  • 解压后
    在这里插入图片描述

  • 导入虚拟机环境中

  • 关于docker的build和up就轻车熟路了

  • 先看看PDF的任务吧

操作步骤

  • 包嗅探和欺骗是网络安全中的两个重要概念;它们是网络通信中 的两大威胁。能够理解这两种威胁对于理解网络中的安全措施至关重 要。有许多包嗅探和欺骗工具,如 Wireshark、Tcpdump、Netwox 等。 其中一些工具被安全专家以及攻击者广泛使用。能够使用这些工具对 学生来说很重要,但对于网络安全课程的学生来说,更重要的是了解 这些工具是如何工作的,即包嗅探和欺骗是如何在软件中实现的。 本实验的目标是让学生掌握大多数嗅探和欺骗工具的基本技术。 学生们将使用一些简单的嗅探和欺骗程序,阅读它们的源代码,修改 它们,并最终对这些程序的技术方面有深入的了解。在本实验结束时, 学生应该能够编写自己的嗅探和欺骗程序。
  • 数据包嗅探和欺骗是网络安全中的两个重要概念;它们是网络通信中的两个主要威胁。能够理解这两种威胁对于理解网络中的安全措施至关重要。有许多数据包嗅探和欺骗工具,如线鲨,Tcpdump,Netwox,Scapy等。其中一些工具已被安全专家和攻击者广泛使用。能够使用这些工具对学生来说很重要,但对于网络安全课程中的学生来说,更重要的是了解这些工具是如何工作的,即数据包嗅探和欺骗是如何在软件中实现的。这个实验室的目标有两个方面:学习使用这些工具和理解这些工具背后的技术。对于第二个目标,学生将编写简单的嗅探器和欺骗程序,并获得一个深入的了解这些程序的技术方面。本实验室涵盖以下主题:
  • How the sniffing and spoofing work
  • Packet sniffing using the pcap library and Scapy
  • Packet spoofing using raw socket and Scapy
  • Manipulating packets using Scapy

Lab Task Set 1: Using Scapy to Sniff and Spoof Packets

  • 许多工具可以用来做嗅探和欺骗,但其中大多数只提供固定的功能。Scapy是不同的:它不仅可以作为一个工具,还可以作为一个构建块来构建其他的嗅探和欺骗工具,也就是说,我们可以将Scapy功能集成到我们自己的程序中。在这组任务中,我们将对每个任务使用Scapy。要使用Scapy,我们可以编写一个Python程序,然后使用Python执行这个程序。请参阅下面的示例。我们应该使用根权限运行Python,因为欺骗数据包需要该特权。在程序的开始(第➀行),我们应该导入所有的Scapy的模块。
Task 1.1: Sniffing Packets
  • 安装并启动docker

在这里插入图片描述

  • 这部分主要是利用工具来嗅探数据包,这里用的是 scapy。 可以用下面的命令进行安装。
sudo pip3 install scapy

在这里插入图片描述

task1.1A
  • 下面是使用 scapy来嗅探数据包的一个例子:
  • 代码:
    在这里插入图片描述
  • 代码简单就上图了
  • 先使用如下命令添加执行权限:
chmod a+x sniffer.py 

在这里插入图片描述

  • ifconfig查看本机IP
    在这里插入图片描述
  • 手贱PING一下

在这里插入图片描述

  • 先使用root权限运行上面的程序 sudo ./sniffer.py, 结果如下,可以看到其成功嗅探到了不同协议的数据包,图中只包括ICMP包。
    在这里插入图片描述在这里插入图片描述
  • 然后使用普通权限运行该程序 ./sniffer.py。结果如下,可以看到报错了,提示无权限。
    在这里插入图片描述
  • 这说明嗅探包是一件拥有高权限才能做的事情,没有高权限,系统是不让你嗅探数据包的。
task1.1B
  • 一般在嗅探包时我们只对特定类型的数据包感兴趣,所以我们需要对数据包进行一些过滤。scapy的过滤机制使用BPF的语法,这部分我们需要实现几个过滤的方法。
  • 通常,当我们嗅探数据包时,我们只对某些类型的数据包感兴趣。我们可以通过在嗅探中设置过滤器来实现这一点。Scapy的过滤器使用BPF(伯克利数据包过滤器)语法;你可以找到SBPF手册从互联网上提供。请设置以下过滤器,并再次演示您的嗅探器程序(每个过滤器应单独设置)
  • 仅捕获ICMP包捕获来自特定IP和目标端口号为23的任何TCP包。•捕获数据包来自或转到一个特定的子网。您可以选择任何子网,如128.230.0.0/16;您不应该选择虚拟机连接到的子网。
  • 只捕捉ICMP数据包,代码修改如下:
    在这里插入图片描述
  • 手再PING试一下

在这里插入图片描述

  • 运行结果如下,可以看到捕获到了ICMP数据包:
    在这里插入图片描述
  • 只捕捉来自特定IP,且目标端口号为23的TCP数据包,查看自己的IP地址如下:
    在这里插入图片描述
  • 本机ip地址:10.0.2.1
  • 设定一个ip地址:10.0.2.2
  • 创建发送数据包的代码:datapak.py、并指定tcp端口是23
  • 修改sniffer.py文件:
    在这里插入图片描述
  • 运行

在这里插入图片描述

  • 捕获了前三次发的包

在这里插入图片描述

  • 捕获来自或去往特定子网的数据包。您可以选择任何子网,如128 . 230 . 0 . 0/16;您不应该选择虚拟机所连接的子网
    修改嗅探的过滤条件:
    在这里插入图片描述
#!/usr/bin/python3
from scapy.all import *ip = IP()
ip.src ="10.0.2.4"
ip.dst ="192.169.0.1"tcp=TCP()
tcp.dport =23
send(ip/tcp)
  • 修改datapak.py文件:
    在这里插入图片描述
    在这里插入图片描述
  • 嗅探结果如下:
    在这里插入图片描述
Task 1.2: Spoofing ICMP Packets
  • 作为一个数据包欺骗工具,Scapy允许我们将IP数据包的字段设置为任意值。此任务的目的是用任意的源IP地址来欺骗IP数据包。我们将欺骗ICMP回波请求包,并将它们发送到同一网络上的另一个虚拟机。我们将使用线鲨来观察我们的请求是否会被接收人接受。如果它被接受,一个回波回复包将被发送到欺骗的IP地址。下面的代码展示了如何欺骗ICMP数据包的一个示例。
>>> from scapy.all import *
>>> a = IP()>>> a.dst =10.0.2.3’ ➁
>>> b = ICMP()>>> p = a/b ➃
>>> send(p).
Sent 1 packets.
  • 在上面的代码中,行➀从IP类创建一个IP对象;为每个IP头字段定义一个类属性。我们可以使用ls(a)或ls(IP)来查看所有的属性名称/值。我们也可以使用。show()和IP.show()来这样做。第➁行显示了如何设置目标IP地址字段。如果未设置字段,则将使用默认值。
  • 行➂创建了一个ICMP对象。默认类型是echo请求。在第➃行中,我们将a和b堆叠在一起以形成一个新对象。/操作符被IP类重载,因此它不再表示划分;相反,它意味着将b添加到a作为a的有效负载字段,并相应地修改a的字段。因此,我们得到了一个表示ICMP数据包的新对象。我们现在可以使用行➄中发送()发送这个包。请对示例代码进行任何必要的更改,然后证明您可以用任意的源IP地址欺骗ICMP回波请求包。
  • 安装wireshark:
sudo apt-get update
sudo apt-get install wireshark

在这里插入图片描述

  • 启动wireshark:
  • sudo wireshark:(root权限下、报错忽略)
  • 准备抓包:

在这里插入图片描述

  • 运行发包程序:
#!/usr/bin/python3
from scapy.all import *ip = IP()
ip.src ="10.0.2.4"
ip.dst ="192.169.0.1"icmp=ICMP()
send(ip/icmp)

在这里插入图片描述
在这里插入图片描述

Task 1.3: Traceroute
  • 此任务的目的是使用Scapy来估计虚拟机和选定目的地之间的路由器数量方面的距离。这基本上是由跟踪工具实现的。在这个任务中,我们将编写我们自己的工具。这个想法非常简单:只需发送一个数据包(任何类型)到目的地,首先将其实时时间(TTL)字段设置为1。这个数据包将被第一个路由器丢弃,该路由器将向我们发送一个ICMP错误消息,告诉我们它的运行时间已经超过。这就是我们如何得到第一个路由器的IP地址。然后,我们将TTL字段增加到2,发送另一个数据包,并获得第二个路由器的IP地址。我们将重复此过程,直到我们的数据包最终到达目的地。需要注意的是,这个实验只得到一个估计结果,因为理论上,不是所有这些包采取相同的路径(但在实际中,它们可能在短时间内)。下面的代码显示了这个过程中的一轮。
a = IP()
a.dst =1.2.3.4’
a.ttl = 3
b = ICMP()
send(a/b)
  • 如果您是一个经验丰富的Python程序员,您可以编写工具来自动执行整个过程。如果您是Python编程的新手,您可以通过手动更改TTL字段,并根据Wireshark的观察记录IP地址。这两种方法都是可以接受的,只要你得到了结果。
  • 模拟一个traceroute,循环每次TTL+1,中间节点都发回ICMP TTL字段过期的错误信息,目的节点发回ICMP reply就结束:
  • 创建一个trace.py文件:
    在这里插入图片描述
from scapy.all import *
import sysdef traceroute(target, minttl=1, maxttl=30, dport=80):print("target: %s(port=%s)" % (target, dport))ans, unans = sr(IP(dst=target, ttl=(minttl,maxttl),id=RandShort())/TCP(flags=0x2, dport=dport), timeout=10)for snd,rcv in ans:print(snd.ttl, rcv.src)if __name__ == '__main__':if len(sys.argv) <= 1:traceroute("baidu.com")else:traceroute(sys.argv[1])
  • 运行结果如下所示

在这里插入图片描述

Task 1.4: Sniffing and-then Spoofing
  • 在此任务中,您将结合嗅探和欺骗技术来实现以下嗅探和欺骗程序。您需要在同一局域网上的两台机器:虚拟机和用户容器。从用户容器中,您可以生成一个IPX。这将生成一个ICMP回波请求包。如果X被激活,ping程序将收到一个回波响应,并打印出响应。您的嗅探和欺骗程序运行在VM上,它通过数据包嗅探来监视局域网。每当它看到ICMP回波请求时,无论目标IP地址是什么,您的程序都应该立即使用数据包欺骗技术发送回波回复。因此,无论机器X是否活动,ping程序将始终收到回复,表明X激活。您需要使用Scapy来完成此任务。在您的报告中,您需要提供证据来证明您的技术是有效的。在您的实验中,您应该从用户容器中获取以下三个IP地址。报告你的观察结果,并解释这些结果。
  • 提示:您需要解释ARP协议是如何工作的,以便正确地解释您的观察结果。您还需要了解一点关于路由的知识。以下命令可帮助您找到指定目的地的路由器:
  • 创建sniffer2.py
    在这里插入图片描述
    在这里插入图片描述
#!/usr/bin/python3
from scapy.all import *def print_pkt(pkt):send(IP(src=pkt[IP].dst, dst=pkt[IP].src)/ICMP(type="echo-reply", code= 0, id=pkt[ICMP].id, seq=pkt[ICMP].seq))pkt = sniff(filter="icmp[icmptype]==icmp-echo",prn=print_pkt)
  • 运行结果如下

在这里插入图片描述

Task 2.1
Task 2.1A: Understanding How a Sniffer Works
  • 可以使用pcap库很容易地编写嗅探器程序。有了pcap,嗅探器的任务就变成了调用pcap库中的一个简单的过程序列。在序列的最后,一旦数据包被捕获,就将被放入缓冲区中进行进一步处理。数据包捕获的所有细节都由pcap库处理。SEED的书提供了一个示例代码,展示了如何使用pcap编写一个简单的嗅探器程序。我们在下面包括了示例代码(详细说明请参阅本书)。
  • 在这个任务中,学生需要编写一个嗅探器程序来打印出每个捕获的数据包的源和目标IP地址。学生可以输入上面的代码或从SEED书的网站(https://www.handsonsecurity。net/figurecode.html)。学生应该提供屏幕截图作为证据,以表明他们的嗅探程序可以成功运行,并产生预期的结果。另外,请回答以下问题:
  • 这部分主要是写一个打印捕获的包的源IP和目的IP地址。代码如下:
    在这里插入图片描述
#include <pcap.h>
#include <stdio.h>
#include <arpa/inet.h>/* Ethernet header */
struct ethheader {u_char  ether_dhost[6]; /* destination host address */u_char  ether_shost[6]; /* source host address */u_short ether_type;     /* protocol type (IP, ARP, RARP, etc) */
};/* IP Header */
struct ipheader {unsigned char      iph_ihl:4, //IP header lengthiph_ver:4; //IP versionunsigned char      iph_tos; //Type of serviceunsigned short int iph_len; //IP Packet length (data + header)unsigned short int iph_ident; //Identificationunsigned short int iph_flag:3, //Fragmentation flagsiph_offset:13; //Flags offsetunsigned char      iph_ttl; //Time to Liveunsigned char      iph_protocol; //Protocol typeunsigned short int iph_chksum; //IP datagram checksumstruct  in_addr    iph_sourceip; //Source IP addressstruct  in_addr    iph_destip;   //Destination IP address
};void got_packet(u_char *args, const struct pcap_pkthdr *header,const u_char *packet)
{struct ethheader *eth = (struct ethheader *)packet;if (ntohs(eth->ether_type) == 0x0800) { // 0x0800 is IP typestruct ipheader * ip = (struct ipheader *)(packet + sizeof(struct ethheader)); printf("       From: %s\n", inet_ntoa(ip->iph_sourceip));   printf("         To: %s\n", inet_ntoa(ip->iph_destip));    /* determine protocol */switch(ip->iph_protocol) {                                 case IPPROTO_TCP:printf("   Protocol: TCP\n\n");return;case IPPROTO_UDP:printf("   Protocol: UDP\n\n");return;case IPPROTO_ICMP:printf("   Protocol: ICMP\n\n");return;default:printf("   Protocol: others\n\n");return;}}
}int main()
{pcap_t *handle;char errbuf[PCAP_ERRBUF_SIZE];struct bpf_program fp;char filter_exp[] = "tcp and dst portrange 10-100";bpf_u_int32 net;// Step 1: Open live pcap session on NIC with name enp0s3handle = pcap_open_live("enp0s3", BUFSIZ, 1, 1000, errbuf);printf("listening on network card, ret: %p...\n", handle);// Step 2: Compile filter_exp into BPF psuedo-codeprintf("try to compile filter...\n");pcap_compile(handle, &fp, filter_exp, 0, net);printf("try to set filter...\n");pcap_setfilter(handle, &fp);// Step 3: Capture packetsprintf("start to sniff...\n");pcap_loop(handle, -1, got_packet, NULL);pcap_close(handle);   //Close the handlereturn 0;
}
  • 使用如下命令编译:
gcc -o sniff sniff.c -lpcap
  • 运行,并尝试ping baidu.com,可以看到发送的包出现在结果中:

  • 运行的结果如下:
    在这里插入图片描述

  • ping
    在这里插入图片描述

在这里插入图片描述

  • Q1: 描述在你的嗅探程序中的库函数的调用
  • A1: 第一步,启动pcap监听网卡。
    • 第二步就是编译BPF过滤器并设置过滤器。
    • 第三步就是设置嗅探的处理函数。
    • 最后关闭嗅探即可。
  • Q2: 为什么需要root权限才能运行嗅探程序?不使用root权限运行该程序会在哪里报错?
  • A2: 嗅探数据包是一个高权限的操作,因为涉及到隐私,安全相关问题。如果普通用户也能嗅探数据包,那么他就能窃取别人的隐私,甚至盗取账号密码等等。不使用root权限运行该程序。对比如下,可以看到在没有权限时第一步监听网卡就失败了:
  • Q3: 打开嗅探程序的混杂模式。打开和关闭这个模式有什么区别?
  • A3: 使用混杂模式可以监听所在网段下其他机器的数据包,关闭则不能。打开混杂模式,可以监听到本网段的机器 ping baidu.com的数据包,关闭后则嗅探不到。
Task 2.1B: Writing Filters
  • 这部分主要是写一些过滤器。这部分还是复用 task 2.1A的代码,只是修改其中的过滤器而已。Pcap过滤器的例子:
  • 只捕捉两个特定主机之间的ICMP包,使用的过滤器为 icmp and src hostand dst host 10.0.2.4, 只捕捉从 发送到 10.0.2.4的ICMP包。、
  • 这边改成了百度的IP
    在这里插入图片描述
  • 结果如下,可以看到全是从百度IP发送到 10.0.2.4的ICMP包,没有其他类型的包。
    在这里插入图片描述
    在这里插入图片描述
  • 捕捉目的端口在10到100之间的TCP包:
    在这里插入图片描述
  • 结果如下,可以看到全是从 10.0.2.15 发送到 10.0.2.4的ICMP包,没有其他类型的包。
  • 捕捉目的端口在10到100之间的TCP包:使用的过滤器为 tcp and dst portrange 10-100, 只捕捉从 10.0.2.15 发送到 10.0.2.4的ICMP包。
  • 结果如下,用浏览器访问baidu.com的包出现在结果中,用浏览器访baidu.com:111的包没有出现在结果中。
    在这里插入图片描述
Task2.1C: Sniffing Passwords
  • 当普通用户发送数据包时,操作系统通常不允许用户设置协议头中的所有字段(如TCP、UDP和IP头)。操作系统将设置大部分字段,而只允许用户设置少数字段,如目标IP地址、目标端口号等。但是,如果用户具有根权限,他们可以在数据包头中设置任何任意字段。这被称为数据包欺骗,它可以通过原始套接字来完成。原始套接字为程序员提供了对数据包构造的绝对控制,允许程序员构造任何任意的数据包,包括设置头字段和有效负载。使用原始套接字非常简单;它涉及四个步骤:(1)创建一个原始套接字,(2)集套接字选项,(3)构建数据包,以及(4)通过原始套接字发送数据包。有许多在线教程可以教您如何在C编程中使用原始套接字。我们已经将一些教程链接到该实验室的网页。请阅读它们,并学习如何编写一个数据包欺骗程序。我们展示了这样一个程序的一个简单的骨架。

  • 嗅探密码。请说明当有人在您监控的网络上使用telnet时,您如何使用嗅探器程序来捕获密码。您可能需要修改您的嗅探器代码来打印出捕获的TCP数据包的数据部分(telnet使用TCP)。如果您打印出整个数据部分,然后手动标记密码(或部分密码)的位置,这是可以接受的。

  • 这边可以看到运行代码之后对tcp包的截获情况

在这里插入图片描述

Task 2.2
  • myheader.h
/* Ethernet header */
struct ethheader {u_char  ether_dhost[6];    /* destination host address */u_char  ether_shost[6];    /* source host address */u_short ether_type;                     /* IP? ARP? RARP? etc */
};/* IP Header */
struct ipheader {unsigned char      iph_ihl:4, //IP header lengthiph_ver:4; //IP versionunsigned char      iph_tos; //Type of serviceunsigned short int iph_len; //IP Packet length (data + header)unsigned short int iph_ident; //Identificationunsigned short int iph_flag:3, //Fragmentation flagsiph_offset:13; //Flags offsetunsigned char      iph_ttl; //Time to Liveunsigned char      iph_protocol; //Protocol typeunsigned short int iph_chksum; //IP datagram checksumstruct  in_addr    iph_sourceip; //Source IP addressstruct  in_addr    iph_destip;   //Destination IP address
};/* ICMP Header  */
struct icmpheader {unsigned char icmp_type; // ICMP message typeunsigned char icmp_code; // Error codeunsigned short int icmp_chksum; //Checksum for ICMP Header and dataunsigned short int icmp_id;     //Used for identifying requestunsigned short int icmp_seq;    //Sequence number
};/* UDP Header */
struct udpheader
{u_int16_t udp_sport;           /* source port */u_int16_t udp_dport;           /* destination port */u_int16_t udp_ulen;            /* udp length */u_int16_t udp_sum;             /* udp checksum */
};/* TCP Header */
struct tcpheader {u_short tcp_sport;               /* source port */u_short tcp_dport;               /* destination port */u_int   tcp_seq;                 /* sequence number */u_int   tcp_ack;                 /* acknowledgement number */u_char  tcp_offx2;               /* data offset, rsvd */
#define TH_OFF(th)      (((th)->tcp_offx2 & 0xf0) >> 4)u_char  tcp_flags;
#define TH_FIN  0x01
#define TH_SYN  0x02
#define TH_RST  0x04
#define TH_PUSH 0x08
#define TH_ACK  0x10
#define TH_URG  0x20
#define TH_ECE  0x40
#define TH_CWR  0x80
#define TH_FLAGS        (TH_FIN|TH_SYN|TH_RST|TH_ACK|TH_URG|TH_ECE|TH_CWR)u_short tcp_win;                 /* window */u_short tcp_sum;                 /* checksum */u_short tcp_urp;                 /* urgent pointer */
};/* Psuedo TCP header */
struct pseudo_tcp
{unsigned saddr, daddr;unsigned char mbz;unsigned char ptcl;unsigned short tcpl;struct tcpheader tcp;char payload[1500];
};
  • checksum.c
#include <unistd.h>
#include <stdio.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/ip.h>
#include <arpa/inet.h>#include "myheader.h"unsigned short in_cksum (unsigned short *buf, int length)
{unsigned short *w = buf;int nleft = length;int sum = 0;unsigned short temp=0;/** The algorithm uses a 32 bit accumulator (sum), adds* sequential 16 bit words to it, and at the end, folds back all* the carry bits from the top 16 bits into the lower 16 bits.*/while (nleft > 1)  {sum += *w++;nleft -= 2;}/* treat the odd byte at the end, if any */if (nleft == 1) {*(u_char *)(&temp) = *(u_char *)w ;sum += temp;}/* add back carry outs from top 16 bits to low 16 bits */sum = (sum >> 16) + (sum & 0xffff);  // add hi 16 to low 16sum += (sum >> 16);                  // add carryreturn (unsigned short)(~sum);
}/****************************************************************TCP checksum is calculated on the pseudo header, which includesthe TCP header and data, plus some part of the IP header.Therefore, we need to construct the pseudo header first.
*****************************************************************/unsigned short calculate_tcp_checksum(struct ipheader *ip)
{struct tcpheader *tcp = (struct tcpheader *)((u_char *)ip +sizeof(struct ipheader));int tcp_len = ntohs(ip->iph_len) - sizeof(struct ipheader);/* pseudo tcp header for the checksum computation */struct pseudo_tcp p_tcp;memset(&p_tcp, 0x0, sizeof(struct pseudo_tcp));p_tcp.saddr  = ip->iph_sourceip.s_addr;p_tcp.daddr  = ip->iph_destip.s_addr;p_tcp.mbz    = 0;p_tcp.ptcl   = IPPROTO_TCP;p_tcp.tcpl   = htons(tcp_len);memcpy(&p_tcp.tcp, tcp, tcp_len);return  (unsigned short) in_cksum((unsigned short *)&p_tcp,tcp_len + 12);
}
Task 2.2A: Write a spoofing program
  • 请用c编写您自己的数据包欺骗程序。您需要提供证据(例如,有线鲨鱼数据包跟踪),以表明您的程序成功地发送了欺骗的IP数据包。
  • 这部分主要是伪造IP包。这里伪造是UDP包, 代码如下:
  • spoof.c
#include <unistd.h>
#include <stdio.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/ip.h>
#include <arpa/inet.h>#include "myheader.h"/*************************************************************Given an IP packet, send it out using a raw socket.
**************************************************************/
void send_raw_ip_packet(struct ipheader* ip)
{struct sockaddr_in dest_info;int enable = 1;// Step 1: Create a raw network socket.int sock = socket(AF_INET, SOCK_RAW, IPPROTO_RAW);printf("sock: %d\n", sock);// Step 2: Set socket option.setsockopt(sock, IPPROTO_IP, IP_HDRINCL,&enable, sizeof(enable));// Step 3: Provide needed information about destination.dest_info.sin_family = AF_INET;dest_info.sin_addr = ip->iph_destip;// Step 4: Send the packet out.sendto(sock, ip, ntohs(ip->iph_len), 0,(struct sockaddr *)&dest_info, sizeof(dest_info));close(sock);
}
  • task22A
#include <unistd.h>
#include <stdio.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/ip.h>
#include <arpa/inet.h>#include "myheader.h"void   send_raw_ip_packet (struct ipheader* ip);/******************************************************************Spoof a UDP packet using an arbitrary source IP Address and port
*******************************************************************/
int main() {char buffer[1500];memset(buffer, 0, 1500);struct ipheader *ip = (struct ipheader *) buffer;struct udpheader *udp = (struct udpheader *) (buffer +sizeof(struct ipheader));/*********************************************************Step 1: Fill in the UDP data field.********************************************************/char *data = buffer + sizeof(struct ipheader) +sizeof(struct udpheader);const char *msg = "Hello Server!\n";int data_len = strlen(msg);strncpy (data, msg, data_len);/*********************************************************Step 2: Fill in the UDP header.********************************************************/udp->udp_sport = htons(12345);udp->udp_dport = htons(9090);udp->udp_ulen = htons(sizeof(struct udpheader) + data_len);udp->udp_sum =  0; /* Many OSes ignore this field, so we do notcalculate it. *//*********************************************************Step 3: Fill in the IP header.********************************************************/ip->iph_ver = 4;ip->iph_ihl = 5;ip->iph_ttl = 20;ip->iph_sourceip.s_addr = inet_addr("1.1.1.1");ip->iph_destip.s_addr = inet_addr("8.8.8.8");ip->iph_protocol = IPPROTO_UDP; // The value is 17.ip->iph_len = htons(sizeof(struct ipheader) +sizeof(struct udpheader) + data_len);/*********************************************************Step 4: Finally, send the spoofed packet********************************************************/send_raw_ip_packet (ip);return 0;
}
  • 使用gcc -o task22A task22A.c spoof.c -lpcap编译,sudo ./task22A运行,查看后台wireshark,可以看到我们伪造的UDP包

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

Task 2.2B: Spoof an ICMP Echo Request
  • 这部分是伪造ICMP Echo请求。伪造的代码如下, 其中源IP10.0.2.5是局域网内另一个虚拟机的IP,
    在这里插入图片描述
  • task22B.c
#include <unistd.h>
#include <stdio.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/ip.h>
#include <arpa/inet.h>#include "myheader.h"unsigned short in_cksum (unsigned short *buf, int length);
void send_raw_ip_packet(struct ipheader* ip);/******************************************************************Spoof an ICMP echo request using an arbitrary source IP Address
*******************************************************************/
int main() {char buffer[1500];memset(buffer, 0, 1500);/*********************************************************Step 1: Fill in the ICMP header.********************************************************/struct icmpheader *icmp = (struct icmpheader *)(buffer + sizeof(struct ipheader));icmp->icmp_type = 8; //ICMP Type: 8 is request, 0 is reply.// Calculate the checksum for integrityicmp->icmp_chksum = 0;icmp->icmp_chksum = in_cksum((unsigned short *)icmp,sizeof(struct icmpheader));/*********************************************************Step 2: Fill in the IP header.********************************************************/struct ipheader *ip = (struct ipheader *) buffer;ip->iph_ver = 4;ip->iph_ihl = 5;ip->iph_ttl = 20;ip->iph_sourceip.s_addr = inet_addr("10.9.0.5");ip->iph_destip.s_addr = inet_addr("8.8.8.8");ip->iph_protocol = IPPROTO_ICMP;ip->iph_len = htons(sizeof(struct ipheader) +sizeof(struct icmpheader));/*********************************************************Step 3: Finally, send the spoofed packet********************************************************/send_raw_ip_packet (ip);return 0;
}
  • 其中用到额外的文件,
  • 使用gcc -o task22B task22B.c spoof.c checksum.c -lpcap 进行编译, sudo ./task22B运行,查看后台的wireshark,如下:
  • 可以看到我们发送的源IP为10.0.2.5, 目的IP为8.8.8.8的ICMP包,并且还有回复
    在这里插入图片描述
  • Q4: 能把IP包的长度设置为任意数值,而不管实际的包的大小吗?
  • A4: 将代码中设置长度该成下面的代码,运行可知其为28B,修改长度为10B,wireshark没有捕捉到包,说明没有发出去。
  • 修改成1000B,结果如下,可以看到正常发送出去,且收到了相应。说明可以调大length,不能调小length。
  • Q5: 使用 raw socket 编程, 我们要计算IP头部的checksum吗?
  • A5: 不用计算IP头部的checksum,但是需要计算ICMP头部的checksum。
  • Q6: 为什么使用raw socket 编程需要root权限?没有root权限执行时程序会在哪里报错?
  • A6:因为能任意读取发送包意味着很大的安全风险,所以需要root权限。使用普通权限运行结果如下:
    在这里插入图片描述
Task 2.3: Sniff and then Spoof
  • 在此任务中,您将结合嗅探和欺骗技术来实现以下嗅探和欺骗程序。你需要在同一局域网上的两台机器。从机器A开始,你就可以得到一个IPX。这将生成一个ICMP回波请求包。如果X被激活,ping程序将收到一个回波响应,并打印出响应。您的嗅探和欺骗程序在攻击者机器上运行,它通过数据包嗅探监视局域网。每当它看到ICMP回波请求时,无论目标IP地址是什么,您的程序都应该立即使用数据包欺骗技术发送回波回复。因此,无论机器X是否活动,ping程序将始终收到回复,表明X激活。您需要用C编写这样的程序,并在报告中包含屏幕截图,以显示您的程序可以工作。也请在您的报告中附上代码(并有足够数量的评论)。
  • 准备两个在同一个局域网的虚拟机,这部分主要是同时嗅探和伪造包,实现一个机器ping任意IP x,另一个机器伪造ICMP回复请求,使得其有回复,而IP x所对应的机器可能根本不存在。
    准备两个在同一个局域网的虚拟机,这部分主要是同时嗅探和伪造包,实现一个机器ping任意IP x,另一个机器伪造ICMP回复请求,使得其有回复,而IP x所对应的机器可能根本不存在。
  • 代码如下task23.c
#include <pcap.h>
#include <stdio.h>
#include <arpa/inet.h>
#include "myheader.h"void got_packet(u_char *args, const struct pcap_pkthdr *header,const u_char *packet)
{struct ethheader *eth = (struct ethheader *)packet;if (ntohs(eth->ether_type) == 0x0800) { // 0x0800 is IP typestruct ipheader * ip = (struct ipheader *)(packet + sizeof(struct ethheader));printf("From: %s ", inet_ntoa(ip->iph_sourceip));   printf("To: %s ", inet_ntoa(ip->iph_destip));if (ip->iph_protocol == IPPROTO_ICMP)printf("protocal: ICMP\n");elseprintf("protocal: Others\n");struct icmpheader *icmp_pkt = (struct icmpheader *)(packet + sizeof(struct ethheader) + sizeof(struct ipheader));                                                if (ip->iph_protocol == IPPROTO_ICMP) {char buffer[1500];memset(buffer, 0, 1500);/*********************************************************Step 1: Fill in the ICMP header.********************************************************/struct icmpheader *icmp = (struct icmpheader *)(buffer + sizeof(struct ipheader));icmp->icmp_type = 0; //ICMP Type: 8 is request, 0 is reply.icmp->icmp_code = 0;icmp->icmp_id   = icmp_pkt->icmp_id;icmp->icmp_seq  = icmp_pkt->icmp_seq;printf("icmp id: %d, seq: %d\n", ntohs(icmp_pkt->icmp_id), ntohs(icmp_pkt->icmp_seq));// Calculate the checksum for integrityicmp->icmp_chksum = 0;icmp->icmp_chksum = in_cksum((unsigned short *)icmp,sizeof(struct icmpheader));/*********************************************************Step 2: Fill in the IP header.********************************************************/struct ipheader *ipp = (struct ipheader *) buffer;ipp->iph_ver = 4;ipp->iph_ihl = 5;ipp->iph_ttl = 64;ipp->iph_sourceip.s_addr = ip->iph_destip.s_addr;ipp->iph_destip.s_addr = ip->iph_sourceip.s_addr;ipp->iph_protocol = IPPROTO_ICMP;ipp->iph_len = htons(sizeof(struct ipheader) +sizeof(struct icmpheader));printf("send tt source :%s\n", inet_ntoa(ipp->iph_sourceip));printf("send tt dest: %s\n", inet_ntoa(ipp->iph_destip));/*********************************************************Step 3: Finally, send the spoofed packet********************************************************/// icmp_pkt->icmp_type = 0;// icmp_pkt->icmp_code = 0;// icmp->icmp_chksum = 0;// icmp->icmp_chksum = in_cksum((unsigned short *)icmp,//                                 sizeof(struct icmpheader));send_raw_ip_packet (ipp);}}
}int main()
{pcap_t *handle;char errbuf[PCAP_ERRBUF_SIZE];struct bpf_program fp;char filter_exp[] = "icmp[icmptype]==icmp-echo";bpf_u_int32 net;// Step 1: Open live pcap session on NIC with name enp0s3handle = pcap_open_live("enp0s3", BUFSIZ, 1, 1000, errbuf);printf("listening on network card, ret: %p...\n", handle);// Step 2: Compile filter_exp into BPF psuedo-codeprintf("try to compile filter...\n");pcap_compile(handle, &fp, filter_exp, 0, net);printf("try to set filter...\n");pcap_setfilter(handle, &fp);// Step 3: Capture packetsprintf("start to sniff...\n");pcap_loop(handle, -1, got_packet, NULL);pcap_close(handle);   //Close the handlereturn 0;
}
  • 使用 gcc -o task23 task23.c checksum.c spoof.c -lpcap编译程序,sudo ./task23运行
    在这里插入图片描述
  • 使用另一台机器ping 1.1.1.1,此机器运行上面的程序,结果如下:

在这里插入图片描述

这篇关于从入门到入土:[SEED-Lab]- Packet Sniffing and Spoofing Lab|嗅探与欺骗实验|详细说明|实验步骤|实验截图的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/283758

相关文章

Spring Security 从入门到进阶系列教程

Spring Security 入门系列 《保护 Web 应用的安全》 《Spring-Security-入门(一):登录与退出》 《Spring-Security-入门(二):基于数据库验证》 《Spring-Security-入门(三):密码加密》 《Spring-Security-入门(四):自定义-Filter》 《Spring-Security-入门(五):在 Sprin

Zookeeper安装和配置说明

一、Zookeeper的搭建方式 Zookeeper安装方式有三种,单机模式和集群模式以及伪集群模式。 ■ 单机模式:Zookeeper只运行在一台服务器上,适合测试环境; ■ 伪集群模式:就是在一台物理机上运行多个Zookeeper 实例; ■ 集群模式:Zookeeper运行于一个集群上,适合生产环境,这个计算机集群被称为一个“集合体”(ensemble) Zookeeper通过复制来实现

数论入门整理(updating)

一、gcd lcm 基础中的基础,一般用来处理计算第一步什么的,分数化简之类。 LL gcd(LL a, LL b) { return b ? gcd(b, a % b) : a; } <pre name="code" class="cpp">LL lcm(LL a, LL b){LL c = gcd(a, b);return a / c * b;} 例题:

git使用的说明总结

Git使用说明 下载安装(下载地址) macOS: Git - Downloading macOS Windows: Git - Downloading Windows Linux/Unix: Git (git-scm.com) 创建新仓库 本地创建新仓库:创建新文件夹,进入文件夹目录,执行指令 git init ,用以创建新的git 克隆仓库 执行指令用以创建一个本地仓库的

Java 创建图形用户界面(GUI)入门指南(Swing库 JFrame 类)概述

概述 基本概念 Java Swing 的架构 Java Swing 是一个为 Java 设计的 GUI 工具包,是 JAVA 基础类的一部分,基于 Java AWT 构建,提供了一系列轻量级、可定制的图形用户界面(GUI)组件。 与 AWT 相比,Swing 提供了许多比 AWT 更好的屏幕显示元素,更加灵活和可定制,具有更好的跨平台性能。 组件和容器 Java Swing 提供了许多

【IPV6从入门到起飞】5-1 IPV6+Home Assistant(搭建基本环境)

【IPV6从入门到起飞】5-1 IPV6+Home Assistant #搭建基本环境 1 背景2 docker下载 hass3 创建容器4 浏览器访问 hass5 手机APP远程访问hass6 更多玩法 1 背景 既然电脑可以IPV6入站,手机流量可以访问IPV6网络的服务,为什么不在电脑搭建Home Assistant(hass),来控制你的设备呢?@智能家居 @万物互联

poj 2104 and hdu 2665 划分树模板入门题

题意: 给一个数组n(1e5)个数,给一个范围(fr, to, k),求这个范围中第k大的数。 解析: 划分树入门。 bing神的模板。 坑爹的地方是把-l 看成了-1........ 一直re。 代码: poj 2104: #include <iostream>#include <cstdio>#include <cstdlib>#include <al

K8S(Kubernetes)开源的容器编排平台安装步骤详解

K8S(Kubernetes)是一个开源的容器编排平台,用于自动化部署、扩展和管理容器化应用程序。以下是K8S容器编排平台的安装步骤、使用方式及特点的概述: 安装步骤: 安装Docker:K8S需要基于Docker来运行容器化应用程序。首先要在所有节点上安装Docker引擎。 安装Kubernetes Master:在集群中选择一台主机作为Master节点,安装K8S的控制平面组件,如AP

MySQL-CRUD入门1

文章目录 认识配置文件client节点mysql节点mysqld节点 数据的添加(Create)添加一行数据添加多行数据两种添加数据的效率对比 数据的查询(Retrieve)全列查询指定列查询查询中带有表达式关于字面量关于as重命名 临时表引入distinct去重order by 排序关于NULL 认识配置文件 在我们的MySQL服务安装好了之后, 会有一个配置文件, 也就

超强的截图工具:PixPin

你是否还在为寻找一款功能强大、操作简便的截图工具而烦恼?市面上那么多工具,常常让人无从选择。今天,想给大家安利一款神器——PixPin,一款真正解放双手的截图工具。 想象一下,你只需要按下快捷键就能轻松完成多种截图任务,还能快速编辑、标注甚至保存多种格式的图片。这款工具能满足这些需求吗? PixPin不仅支持全屏、窗口、区域截图等基础功能,它还可以进行延时截图,让你捕捉到每个关键画面。不仅如此