gopacket简介
1. gopacket是什么?
gopacket是google出品的golang三方库,质量还是靠的住,项目地址为:github.com/google/gopacket
gopacket到底是什么呢?是个抓取网络数据包的库,这么说可能还有点抽象,但是抓包工具大家可能都使用过。
Windows平台下有Wireshark抓包工具,其底层抓包库是npcap(以前是winpcap);
Linux平台下有Tcpdump,其抓包库是libpcap;
而gopacket库可以说是libpcap和npcap的go封装,提供了更方便的go语言操作接口。
对于抓包库来说,常规功能就是抓包,而网络抓包有以下几个步骤:
1、枚举主机上网络设备的接口
2、针对某一网口进行抓包
3、解析数据包的mac层、ip层、tcp/udp层字段等
4、ip分片重组,或tcp分段重组成上层协议如http协议的数据
5、对上层协议进行头部解析和负载部分解析
2. 应用场景有哪些?
场景1:网络流量分析
对网络设备流量进行实时采集以及数据包分析。
场景2:伪造数据包
不少网络安全工具,需要伪造网络数据包,填充上必要的协议字段后发送给对端设备,从而达到一些目的。
场景3:离线pcap文件的读取和写入
安装部署
2.1 安装libpcap或npcap三方库
在使用gopacket包时,首先要确保在windows平台下安装了npcap或winpcap,或者是在linux平台下安装了libpcap库。
npcap下载地址:https://nmap.org/npcap/
libpcap下载地址:https://www.tcpdump.org/
下载自己电脑对应的操作系统版本的库
如果不想从官网下载libpcap库的话,也可以采用centos的yum命令或ubuntu的apt get命令来进行安装。
2.2 安装gopacket库
go get github.com/google/gopacket
使用方法
3.1 枚举网络设备
package main
import (
"fmt"
"log"
"github.com/google/gopacket/pcap"
)
func main() {
// 得到所有的(网络)设备
devices, err := pcap.FindAllDevs()
if err != nil {
log.Fatal(err)
}
// 打印设备信息
fmt.Println("Devices found:")
for _, device := range devices {
fmt.Println("\nName: ", device.Name)
fmt.Println("Description: ", device.Description)
fmt.Println("Devices addresses: ", device.Description)
for _, address := range device.Addresses {
fmt.Println("- IP address: ", address.IP)
fmt.Println("- Subnet mask: ", address.Netmask)
}
}
}
先调用pcap.FindAllDevs()获取当前主机所有的网络设备,网络设备有哪些属性呢?
// Interface describes a single network interface on a machine.
type Interface struct {
Name string //设备名称
Description string //设备描述信息
Flags uint32
Addresses []InterfaceAddress //网口的地址信息列表
}
// InterfaceAddress describes an address associated with an Interface.
// Currently, it's IPv4/6 specific.
type InterfaceAddress struct {
IP net.IP
Netmask net.IPMask // Netmask may be nil if we were unable to retrieve it.
Broadaddr net.IP // Broadcast address for this IP may be nil
P2P net.IP // P2P destination address for this IP may be nil
}
3.2 打开一个设备进行抓包
package main
import (
"fmt"
"github.com/google/gopacket"
"github.com/google/gopacket/pcap"
"log"
"time"
)
var (
device string = "eth0"
snapshot_len int32 = 1024
promiscuous bool = false
err error
timeout time.Duration = 30 * time.Second
handle *pcap.Handle
)
func main() {
// 打开某一网络设备
handle,