Merging upstream version 2.3.0.
Signed-off-by: Daniel Baumann <daniel@debian.org>
This commit is contained in:
parent
678fe22a2c
commit
248a2fcec1
101 changed files with 2349 additions and 847 deletions
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
* Author Jerry Lundström <jerry@dns-oarc.net>
|
||||
* Copyright (c) 2016-2017, OARC, Inc.
|
||||
* Copyright (c) 2016-2025 OARC, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
|
@ -52,6 +52,7 @@
|
|||
|
||||
static void pcap_thread_callback(u_char* user, const struct pcap_pkthdr* pkthdr, const u_char* pkt, const char* name, int dlt);
|
||||
static void pcap_thread_callback_linux_sll(u_char* user, pcap_thread_packet_t* packet, const u_char* payload, size_t length);
|
||||
static void pcap_thread_callback_linux_sll2(u_char* user, pcap_thread_packet_t* packet, const u_char* payload, size_t length);
|
||||
static void pcap_thread_callback_ether(u_char* user, pcap_thread_packet_t* packet, const u_char* payload, size_t length);
|
||||
static void pcap_thread_callback_null(u_char* user, pcap_thread_packet_t* packet, const u_char* payload, size_t length);
|
||||
static void pcap_thread_callback_loop(u_char* user, pcap_thread_packet_t* packet, const u_char* payload, size_t length);
|
||||
|
@ -719,7 +720,8 @@ int pcap_thread_set_callback_linux_sll(pcap_thread_t* pcap_thread, pcap_thread_l
|
|||
if (!pcap_thread) {
|
||||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_ether
|
||||
if (pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|| pcap_thread->callback_ieee802
|
||||
|
@ -742,12 +744,42 @@ int pcap_thread_set_callback_linux_sll(pcap_thread_t* pcap_thread, pcap_thread_l
|
|||
return PCAP_THREAD_OK;
|
||||
}
|
||||
|
||||
int pcap_thread_set_callback_linux_sll2(pcap_thread_t* pcap_thread, pcap_thread_layer_callback_t callback_linux_sll2)
|
||||
{
|
||||
if (!pcap_thread) {
|
||||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|| pcap_thread->callback_ieee802
|
||||
|| pcap_thread->callback_gre
|
||||
|| pcap_thread->callback_ip
|
||||
|| pcap_thread->callback_ipv4
|
||||
|| pcap_thread->callback_ipv6
|
||||
|| pcap_thread->callback_icmp
|
||||
|| pcap_thread->callback_icmpv6
|
||||
|| pcap_thread->callback_udp
|
||||
|| pcap_thread->callback_tcp) {
|
||||
return PCAP_THREAD_ELAYERCB;
|
||||
}
|
||||
if (pcap_thread->running) {
|
||||
return PCAP_THREAD_ERUNNING;
|
||||
}
|
||||
|
||||
pcap_thread->callback_linux_sll2 = callback_linux_sll2;
|
||||
|
||||
return PCAP_THREAD_OK;
|
||||
}
|
||||
|
||||
int pcap_thread_set_callback_ether(pcap_thread_t* pcap_thread, pcap_thread_layer_callback_t callback_ether)
|
||||
{
|
||||
if (!pcap_thread) {
|
||||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|| pcap_thread->callback_ieee802
|
||||
|
@ -776,6 +808,7 @@ int pcap_thread_set_callback_null(pcap_thread_t* pcap_thread, pcap_thread_layer_
|
|||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_loop
|
||||
|| pcap_thread->callback_ieee802
|
||||
|
@ -804,6 +837,7 @@ int pcap_thread_set_callback_loop(pcap_thread_t* pcap_thread, pcap_thread_layer_
|
|||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_ieee802
|
||||
|
@ -832,6 +866,7 @@ int pcap_thread_set_callback_ieee802(pcap_thread_t* pcap_thread, pcap_thread_lay
|
|||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|
@ -860,6 +895,7 @@ int pcap_thread_set_callback_gre(pcap_thread_t* pcap_thread, pcap_thread_layer_c
|
|||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|
@ -888,6 +924,7 @@ int pcap_thread_set_callback_ip(pcap_thread_t* pcap_thread, pcap_thread_layer_ca
|
|||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|
@ -916,6 +953,7 @@ int pcap_thread_set_callback_ipv4(pcap_thread_t* pcap_thread, pcap_thread_layer_
|
|||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|
@ -968,6 +1006,7 @@ int pcap_thread_set_callback_ipv6(pcap_thread_t* pcap_thread, pcap_thread_layer_
|
|||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|
@ -1020,6 +1059,7 @@ int pcap_thread_set_callback_icmp(pcap_thread_t* pcap_thread, pcap_thread_layer_
|
|||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|
@ -1045,6 +1085,7 @@ int pcap_thread_set_callback_icmpv6(pcap_thread_t* pcap_thread, pcap_thread_laye
|
|||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|
@ -1070,6 +1111,7 @@ int pcap_thread_set_callback_udp(pcap_thread_t* pcap_thread, pcap_thread_layer_c
|
|||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|
@ -1095,6 +1137,7 @@ int pcap_thread_set_callback_tcp(pcap_thread_t* pcap_thread, pcap_thread_layer_c
|
|||
return PCAP_THREAD_EINVAL;
|
||||
}
|
||||
if (pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|
@ -1232,9 +1275,9 @@ static void pcap_thread_callback(u_char* user, const struct pcap_pkthdr* pkthdr,
|
|||
packet.state = PCAP_THREAD_PACKET_OK;
|
||||
|
||||
/*
|
||||
* The header for null is in host byte order but may not be
|
||||
* in the same endian as host if coming from a savefile
|
||||
*/
|
||||
* The header for null is in host byte order but may not be
|
||||
* in the same endian as host if coming from a savefile
|
||||
*/
|
||||
|
||||
if (pcaplist->is_offline && pcap_is_swapped(pcaplist->pcap)) {
|
||||
#if __BYTE_ORDER == __LITTLE_ENDIAN
|
||||
|
@ -1322,7 +1365,26 @@ static void pcap_thread_callback(u_char* user, const struct pcap_pkthdr* pkthdr,
|
|||
pcap_thread_callback_linux_sll((void*)pcaplist, &packet, pkt, length);
|
||||
return;
|
||||
|
||||
/* TODO: These might be interesting to implement
|
||||
case DLT_LINUX_SLL2:
|
||||
layer_trace("dlt_linux_sll2");
|
||||
packet.state = PCAP_THREAD_PACKET_INVALID_LINUX_SLL2;
|
||||
need16(packet.linux_sll2.protocol_type, pkt, length);
|
||||
need16(packet.linux_sll2.reserved, pkt, length);
|
||||
need32(packet.linux_sll2.interface_index, pkt, length);
|
||||
need16(packet.linux_sll2.arphrd_type, pkt, length);
|
||||
need8(packet.linux_sll2.packet_type, pkt, length);
|
||||
need8(packet.linux_sll2.link_layer_address_length, pkt, length);
|
||||
needxb(packet.linux_sll2.link_layer_address, 8, pkt, length);
|
||||
packet.state = PCAP_THREAD_PACKET_OK;
|
||||
packet.have_linux_sll2 = 1;
|
||||
|
||||
if (pcaplist->pcap_thread->callback_linux_sll2)
|
||||
pcaplist->pcap_thread->callback_linux_sll2(pcaplist->user, &packet, pkt, length);
|
||||
else
|
||||
pcap_thread_callback_linux_sll2((void*)pcaplist, &packet, pkt, length);
|
||||
return;
|
||||
|
||||
/* TODO: These might be interesting to implement
|
||||
case DLT_IPNET:
|
||||
case DLT_PKTAP:
|
||||
*/
|
||||
|
@ -1410,6 +1472,77 @@ static void pcap_thread_callback_linux_sll(u_char* user, pcap_thread_packet_t* p
|
|||
}
|
||||
}
|
||||
|
||||
static void pcap_thread_callback_linux_sll2(u_char* user, pcap_thread_packet_t* packet, const u_char* payload, size_t length)
|
||||
{
|
||||
pcap_thread_pcaplist_t* pcaplist = (pcap_thread_pcaplist_t*)user;
|
||||
const u_char* orig = payload;
|
||||
size_t origlength = length;
|
||||
|
||||
if (!pcaplist) {
|
||||
return;
|
||||
}
|
||||
if (!pcaplist->pcap_thread) {
|
||||
return;
|
||||
}
|
||||
if (!packet) {
|
||||
return;
|
||||
}
|
||||
if (!payload) {
|
||||
return;
|
||||
}
|
||||
if (!length) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (packet->have_linux_sll2) {
|
||||
layer_trace("have_linux_sll2");
|
||||
switch (packet->linux_sll2.protocol_type) {
|
||||
case 0x8100: /* 802.1q */
|
||||
case 0x88a8: /* 802.1ad */
|
||||
case 0x9100: /* 802.1 QinQ non-standard */
|
||||
if (packet->have_ieee802hdr)
|
||||
break;
|
||||
|
||||
{
|
||||
uint16_t tci;
|
||||
|
||||
packet->state = PCAP_THREAD_PACKET_INVALID_IEEE802;
|
||||
need16(tci, payload, length);
|
||||
packet->ieee802hdr.pcp = (tci & 0xe000) >> 13;
|
||||
packet->ieee802hdr.dei = (tci & 0x1000) >> 12;
|
||||
packet->ieee802hdr.vid = tci & 0x0fff;
|
||||
need16(packet->ieee802hdr.ether_type, payload, length);
|
||||
packet->state = PCAP_THREAD_PACKET_OK;
|
||||
packet->have_ieee802hdr = 1;
|
||||
}
|
||||
|
||||
if (pcaplist->pcap_thread->callback_ieee802)
|
||||
pcaplist->pcap_thread->callback_ieee802(pcaplist->user, packet, payload, length);
|
||||
else
|
||||
pcap_thread_callback_ieee802((void*)pcaplist, packet, payload, length);
|
||||
return;
|
||||
|
||||
case ETHERTYPE_IP:
|
||||
case ETHERTYPE_IPV6:
|
||||
if (pcaplist->pcap_thread->callback_ip)
|
||||
pcaplist->pcap_thread->callback_ip(pcaplist->user, packet, payload, length);
|
||||
else
|
||||
pcap_thread_callback_ip((void*)pcaplist, packet, payload, length);
|
||||
return;
|
||||
|
||||
default:
|
||||
packet->state = PCAP_THREAD_PACKET_UNSUPPORTED;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (pcaplist->pcap_thread->callback_invalid) {
|
||||
if (packet->state == PCAP_THREAD_PACKET_OK)
|
||||
packet->state = PCAP_THREAD_PACKET_INVALID;
|
||||
pcaplist->pcap_thread->callback_invalid(pcaplist->user, packet, orig, origlength);
|
||||
}
|
||||
}
|
||||
|
||||
static void pcap_thread_callback_ether(u_char* user, pcap_thread_packet_t* packet, const u_char* payload, size_t length)
|
||||
{
|
||||
pcap_thread_pcaplist_t* pcaplist = (pcap_thread_pcaplist_t*)user;
|
||||
|
@ -3206,7 +3339,7 @@ static void* _thread(void* vp)
|
|||
while (pcaplist->running) {
|
||||
pthread_testcancel();
|
||||
ret = pcap_loop(pcaplist->pcap, -1, _callback, (u_char*)pcaplist);
|
||||
if (ret == -1) {
|
||||
if (ret == PCAP_ERROR) {
|
||||
/* TODO: Store pcap_loop() error */
|
||||
break;
|
||||
}
|
||||
|
@ -3244,6 +3377,12 @@ static void _callback2(u_char* user, const struct pcap_pkthdr* pkthdr, const u_c
|
|||
} else {
|
||||
pcaplist->running = 0;
|
||||
}
|
||||
|
||||
if (pcaplist->timedrun
|
||||
&& (pkthdr->ts.tv_sec > pcaplist->end.tv_sec
|
||||
|| (pkthdr->ts.tv_sec == pcaplist->end.tv_sec && (pkthdr->ts.tv_usec * 1000) >= pcaplist->end.tv_nsec))) {
|
||||
pcap_breakloop(pcaplist->pcap);
|
||||
}
|
||||
}
|
||||
|
||||
int pcap_thread_run(pcap_thread_t* pcap_thread)
|
||||
|
@ -3264,18 +3403,19 @@ int pcap_thread_run(pcap_thread_t* pcap_thread)
|
|||
}
|
||||
if (pcap_thread->use_layers
|
||||
&& !(pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|| pcap_thread->callback_ieee802
|
||||
|| pcap_thread->callback_gre
|
||||
|| pcap_thread->callback_ip
|
||||
|| pcap_thread->callback_ipv4
|
||||
|| pcap_thread->callback_ipv6
|
||||
|| pcap_thread->callback_icmp
|
||||
|| pcap_thread->callback_icmpv6
|
||||
|| pcap_thread->callback_udp
|
||||
|| pcap_thread->callback_tcp)) {
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|| pcap_thread->callback_ieee802
|
||||
|| pcap_thread->callback_gre
|
||||
|| pcap_thread->callback_ip
|
||||
|| pcap_thread->callback_ipv4
|
||||
|| pcap_thread->callback_ipv6
|
||||
|| pcap_thread->callback_icmp
|
||||
|| pcap_thread->callback_icmpv6
|
||||
|| pcap_thread->callback_udp
|
||||
|| pcap_thread->callback_tcp)) {
|
||||
return PCAP_THREAD_NOCALLBACK;
|
||||
}
|
||||
if (pcap_thread->running) {
|
||||
|
@ -3529,7 +3669,9 @@ int pcap_thread_run(pcap_thread_t* pcap_thread)
|
|||
pcaplist->ipv6_frag_ctx = pcap_thread->callback_ipv6_frag.new(pcap_thread->callback_ipv6_frag.conf, pcaplist->user);
|
||||
pcaplist->have_ipv6_frag_ctx = 1;
|
||||
}
|
||||
pcaplist->running = 1;
|
||||
pcaplist->running = 1;
|
||||
pcaplist->timedrun = timedrun;
|
||||
pcaplist->end = end;
|
||||
}
|
||||
|
||||
t1.tv_sec = pcap_thread->timeout / 1000;
|
||||
|
@ -3590,12 +3732,13 @@ int pcap_thread_run(pcap_thread_t* pcap_thread)
|
|||
}
|
||||
|
||||
packets = pcap_dispatch(pcaplist->pcap, -1, _callback2, (u_char*)pcaplist);
|
||||
if (packets == -1) {
|
||||
if (packets == PCAP_ERROR) {
|
||||
pcap_thread->status = -1;
|
||||
PCAP_THREAD_SET_ERRBUF(pcap_thread, "pcap_dispatch()");
|
||||
pcap_thread->running = 0;
|
||||
return PCAP_THREAD_EPCAP;
|
||||
} else if (packets == -2 || (pcaplist->is_offline && !packets)) {
|
||||
}
|
||||
if (pcaplist->is_offline && !packets) {
|
||||
pcaplist->running = 0;
|
||||
}
|
||||
}
|
||||
|
@ -3620,18 +3763,19 @@ int pcap_thread_next(pcap_thread_t* pcap_thread)
|
|||
}
|
||||
if (pcap_thread->use_layers
|
||||
&& !(pcap_thread->callback_linux_sll
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|| pcap_thread->callback_ieee802
|
||||
|| pcap_thread->callback_gre
|
||||
|| pcap_thread->callback_ip
|
||||
|| pcap_thread->callback_ipv4
|
||||
|| pcap_thread->callback_ipv6
|
||||
|| pcap_thread->callback_icmp
|
||||
|| pcap_thread->callback_icmpv6
|
||||
|| pcap_thread->callback_udp
|
||||
|| pcap_thread->callback_tcp)) {
|
||||
|| pcap_thread->callback_linux_sll2
|
||||
|| pcap_thread->callback_ether
|
||||
|| pcap_thread->callback_null
|
||||
|| pcap_thread->callback_loop
|
||||
|| pcap_thread->callback_ieee802
|
||||
|| pcap_thread->callback_gre
|
||||
|| pcap_thread->callback_ip
|
||||
|| pcap_thread->callback_ipv4
|
||||
|| pcap_thread->callback_ipv6
|
||||
|| pcap_thread->callback_icmp
|
||||
|| pcap_thread->callback_icmpv6
|
||||
|| pcap_thread->callback_udp
|
||||
|| pcap_thread->callback_tcp)) {
|
||||
return PCAP_THREAD_NOCALLBACK;
|
||||
}
|
||||
if (pcap_thread->running) {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue