#include "stc-plugin-pcap.h"
+#define ENCAPTYPE_ETHERNET 1
+#define ENCAPTYPE_NFLOG 141
+
#define PCAP_IFNAME "ifname"
#define PCAP_NFLOG_GROUP "nflog_group"
#define PCAP_DEV_NAME "dev"
#define PCAP_DEV_NET "net"
#define PCAP_DEV_MASK "mask"
+#define NFLOG_IFNAME "nflog"
+
+typedef struct {
+ u_int32_t ts[4];
+} nflog_timestamp_s;
+
//LCOV_EXCL_START
static GHashTable *g_pcap_tables = NULL;
static bool g_pcap_start_fm = false;
g_thread_unref(data->thread);
FREE(data->ifname);
+ FREE(data->nfname);
FREE(data);
}
return fraction;
}
-static void __pcap_ntp_info(const u_char *packet)
+static void __pcap_ntp_info(const u_char **packet)
{
- ntp_t *ntp_h = (ntp_t *)(packet +
- SIZE_ETHER_HEADER + SIZE_IP_HEADER + SIZE_UDP_HEADER);
+ ntp_t *ntp_h = (ntp_t *)*packet;
char refid[BUFF_SIZE_ID];
char reftime[BUFF_SIZE_TIME];
char orgtime[BUFF_SIZE_TIME];
__pcap_ntp_time_info(ntp_h->rectime.second, rectime);
__pcap_ntp_time_info(ntp_h->xmttime.second, xmttime);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Flags[0x%02x] Stratum[%u] Poll[%u:%us] Precision[%u] "
"Root delay[%u.%06us] Root dispersion[%u.%06us] Ref ID[%s]",
ntp_h->flags, ntp_h->stratum, ntp_h->poll,
__pcap_ntp_fraction_info(ntp_h->rootdisp.fraction),
refid);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Reference[%s] Origin[%s] Receive[%s] Transmit[%s]",
reftime, orgtime, rectime, xmttime);
}
char buf[BOOTP_MOPTION_LEN];
uint8_t *opt = moption;
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Magic cookie[DHCP]");
while(len > 0) {
case DHCP_TAG_SUBNET_MASK:
inet_ntop(AF_INET, (struct in_addr *)data,
addr, BUFF_SIZE_IP);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Subnet mask[%s]", addr);
break;
case DHCP_TAG_ROUTER:
inet_ntop(AF_INET, (struct in_addr *)data,
addr, BUFF_SIZE_IP);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Router[%s]", addr);
break;
case DHCP_TAG_DNS:
inet_ntop(AF_INET, (struct in_addr *)data,
addr, BUFF_SIZE_IP);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Domain name server[%s]", addr);
break;
case DHCP_TAG_HOST_NAME:
snprintf(buf, ((length < BOOTP_MOPTION_LEN) ?
(length + 1) : BOOTP_MOPTION_LEN), "%s", (char *)data);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Host name[%s]", buf);
break;
case DHCP_TAG_REQUESTED_IP:
inet_ntop(AF_INET, (struct in_addr *)data,
addr, BUFF_SIZE_IP);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Requested IP[%s]", addr);
break;
case DHCP_TAG_IP_LEASE_TIME:
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("IP address lease time[%us]",
ntohl(*(uint32_t *)data));
break;
case DHCP_TAG_MSG_TYPE:
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("DHCP message type[%u:%s]", *data,
__pcap_dhcp_msg_type_info(*data));
break;
case DHCP_TAG_SERVER_ID:
inet_ntop(AF_INET, (struct in_addr *)data,
addr, BUFF_SIZE_IP);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("DHCP server identifier[%s]", addr);
break;
case DHCP_TAG_MSG_SIZE:
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Maximum DHCP message size[%u]",
ntohs(*(uint16_t *)data));
break;
case DHCP_TAG_CLIENT_ID:
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Client identifier HW type[0x%02x:%s]", *data,
__pcap_dhcp_client_id_info(*data));
if (*data == DHCP_CLIENT_ID_ETHERNET) {
g_strlcpy(host,
ether_ntoa((const struct ether_addr *)&data[1]),
sizeof(host));
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Client identifier MAC[%s]", host);
}
break;
case DHCP_TAG_END:
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("End");
return;
default:
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Unknown[%u]", tag);
break;
}
return info;
}
-static void __pcap_bootp_info(const u_char *packet)
+static void __pcap_bootp_info(const u_char **packet, u_int16_t len)
{
- udp_t *udp_h = (udp_t *)(packet
- + SIZE_ETHER_HEADER + SIZE_IP_HEADER);
- bootp_t *bootp_h = (bootp_t *)(packet +
- SIZE_ETHER_HEADER + SIZE_IP_HEADER + SIZE_UDP_HEADER);
+ bootp_t *bootp_h = (bootp_t *)*packet;
char ciaddr[BUFF_SIZE_IP];
char yiaddr[BUFF_SIZE_IP];
char siaddr[BUFF_SIZE_IP];
char giaddr[BUFF_SIZE_IP];
char chaddr[BUFF_SIZE_HOST];
- u_int16_t len;
inet_ntop(AF_INET, &bootp_h->ciaddr, ciaddr, BUFF_SIZE_IP);
inet_ntop(AF_INET, &bootp_h->yiaddr, yiaddr, BUFF_SIZE_IP);
ether_ntoa((const struct ether_addr *)bootp_h->chaddr),
sizeof(chaddr));
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Message type[%u:%s] HW type[0x%02x] HW len[%u] Hops[%u] "
"Transaction ID[0x%08x] Seconds elapsed[%u] Flags[0x%04x]",
bootp_h->op, __pcap_bootp_op_info(bootp_h->op),
bootp_h->htype, bootp_h->hlen, bootp_h->hops,
ntohl(bootp_h->xid), ntohs(bootp_h->secs), ntohs(bootp_h->flags));
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Client[%s] Your(client)[%s] Next server[%s] "
"Relay agent[%s] Client MAC[%s]",
ciaddr, yiaddr, siaddr, giaddr, chaddr);
- len = ntohs(udp_h->len);
__pcap_bootp_magic_info(bootp_h->magic, bootp_h->moption, len);
}
return (uint8_t *)nxt;
}
-static void __pcap_dns_data_info(const u_char *packet)
+static void __pcap_dns_data_info(const u_char **packet, dns_t *dns_h)
{
- dns_t *dns_h = (dns_t *)(packet +
- SIZE_ETHER_HEADER + SIZE_IP_HEADER +
- SIZE_UDP_HEADER);
- uint8_t *data = (uint8_t *)(packet +
- SIZE_ETHER_HEADER + SIZE_IP_HEADER +
- SIZE_UDP_HEADER + SIZE_DNS_HEADER);
+ uint8_t *data = (uint8_t *)*packet;
uint16_t qdcount = ntohs(dns_h->questions);
uint16_t ancount = ntohs(dns_h->answerRR);
int i = 0;
uint16_t class;
if (i == 0) {
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("[Queries]");
}
type = ntohs(*(uint16_t *)&data[0]);
class = ntohs(*(uint16_t *)&data[2]);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Name[%s] Type[%u:%s] Class[0x%04x:%s]",
name, type, __pcap_dns_type_info(type),
class, __pcap_dns_class_info(class));
char ip[BUFF_SIZE_IP];
if (i == 0) {
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("[Answers]");
}
case DNS_QTYPE_A:
inet_ntop(AF_INET, (struct in_addr *)&data[10],
ip, BUFF_SIZE_IP);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Name[%s] Type[%u:%s] Class[0x%04x:%s] "
"TTL[%u] Data length[%u] Address[%s]",
name, type, __pcap_dns_type_info(type),
__pcap_dns_name_info((uint8_t *)dns_h, &data[10], cname);
if (data == NULL)
return;
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Name[%s] Type[%u:%s] Class[0x%04x:%s] "
"TTL[%u] Data length[%u] CName[%s]",
name, type, __pcap_dns_type_info(type),
case DNS_QTYPE_AAAA:
break;
default:
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Name[%s] Type[%u:%s] Class[0x%04x:%s] "
"TTL[%u] Data length[%u]",
name, type, __pcap_dns_type_info(type),
}
}
-static void __pcap_dns_info(const u_char *packet)
+static void __pcap_dns_info(const u_char **packet)
{
- dns_t *dns_h = (dns_t *)(packet +
- SIZE_ETHER_HEADER + SIZE_IP_HEADER + SIZE_UDP_HEADER);
+ dns_t *dns_h = (dns_t *)*packet;
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Transaction ID[0x%x] Flags[0x%x] Questions[%u] "
"Answer RRs[%u] Authority RRs[%u] Additional RRs[%u]",
ntohs(dns_h->id), ntohs(dns_h->flags),
ntohs(dns_h->questions), ntohs(dns_h->answerRR),
ntohs(dns_h->authorityRR), ntohs(dns_h->additionalRR));
- __pcap_dns_data_info(packet);
+ *packet += SIZE_DNS_HEADER;
+
+ __pcap_dns_data_info(packet, dns_h);
}
static const char *__pcap_icmp_code_info(u_int8_t type, u_int8_t code)
return info;
}
-static void __pcap_icmp_info(const u_char *packet)
+static void __pcap_icmp_info(const u_char **packet)
{
- icmp_t *icmp_h = (icmp_t *)(packet +
- SIZE_ETHER_HEADER + SIZE_IP_HEADER);
+ icmp_t *icmp_h = (icmp_t *)*packet;
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Type[%u:%s] Code[%u:%s] Checksum[0x%x]",
icmp_h->type, __pcap_icmp_type_info(icmp_h->type),
icmp_h->code, __pcap_icmp_code_info(icmp_h->type, icmp_h->code),
ntohs(icmp_h->checksum));
}
-static void __pcap_tcp_info(const u_char *packet)
+static void __pcap_tcp_info(const u_char **packet)
{
- tcp_t *tcp_h = (tcp_t *)(packet +
- SIZE_ETHER_HEADER + SIZE_IP_HEADER);
+ tcp_t *tcp_h = (tcp_t *)*packet;
u_int16_t source = ntohs(tcp_h->source);
u_int16_t dest = ntohs(tcp_h->dest);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Source[%u] Destination[%u] Sequence[%u] "
"Acknowledgment seq[%u] Window size[%u] ",
ntohs(tcp_h->source), ntohs(tcp_h->dest),
ntohl(tcp_h->seq), ntohl(tcp_h->ack_seq),
ntohs(tcp_h->window));
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Checksum[0x%x] URG[%u] ACK[%u] PUSH[%u] "
"RST[%u] SYN[%u] FIN[%u]",
ntohs(tcp_h->check),
tcp_h->urg, tcp_h->ack, tcp_h->psh,
tcp_h->rst, tcp_h->syn, tcp_h->fin);
+ *packet += SIZE_TCP_HEADER;
+
if (IS_SRC_OR_DST_PORT(PORT_DNS))
__pcap_dns_info(packet);
}
-static void __pcap_udp_info(const u_char *packet)
+static void __pcap_udp_info(const u_char **packet)
{
- udp_t *udp_h = (udp_t *)(packet
- + SIZE_ETHER_HEADER + SIZE_IP_HEADER);
+ udp_t *udp_h = (udp_t *)*packet;
u_int16_t source = ntohs(udp_h->source);
u_int16_t dest = ntohs(udp_h->dest);
+ u_int16_t len = ntohs(udp_h->len);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Source[%u] Destination[%u] Len[%u] Checksum[0x%x]",
- source, dest, ntohs(udp_h->len), ntohs(udp_h->check));
+ source, dest, len, ntohs(udp_h->check));
+
+ *packet += SIZE_UDP_HEADER;
if (IS_SRC_OR_DST_PORT(PORT_DNS))
__pcap_dns_info(packet);
else if (IS_SRC_OR_DST_PORT(PORT_BOOTP_C) ||
IS_SRC_OR_DST_PORT(PORT_BOOTP_S))
- __pcap_bootp_info(packet);
+ __pcap_bootp_info(packet, len);
else if (IS_SRC_OR_DST_PORT(PORT_NTP))
__pcap_ntp_info(packet);
}
return info;
}
-static void __pcap_arp_info(const u_char *packet)
+static void __pcap_arp_info(const u_char **packet)
{
- arp_t *arp_h = (arp_t *)(packet + SIZE_ETHER_HEADER);
- u_int8_t *sha = (u_int8_t *)(packet +
- SIZE_ETHER_HEADER + SIZE_ARP_HEADER);
+ arp_t *arp_h = (arp_t *)*packet;
+ u_int8_t *sha = (u_int8_t *)(*packet + SIZE_ARP_HEADER);
u_int8_t *spa = (u_int8_t *)(sha + arp_h->ar_hln);
u_int8_t *tha = (u_int8_t *)(spa + arp_h->ar_pln);
u_int8_t *tpa = (u_int8_t *)(tha + arp_h->ar_hln);
ar_pro = ntohs(arp_h->ar_pro);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("HW type[%u] Protocol type[0x%04x:%s] "
"HW size[%u] Protocol size[%u] Opcode[%u:%s] ",
ntohs(arp_h->ar_hrd), ar_pro,
arp_h->ar_hln, arp_h->ar_pln,
ar_op, __pcap_arp_opcode_info(ar_op));
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Sender MAC[%s] Sender IP[%s] "
"Target MAC[%s] Target IP[%s]",
sma, sia, tma, tia);
return info;
}
-static void __pcap_ipv6_info(const u_char *packet)
+static void __pcap_ipv6_info(const u_char **packet)
{
- ip6_t *ip6_h = (ip6_t *)(packet + SIZE_ETHER_HEADER);
+ ip6_t *ip6_h = (ip6_t *)*packet;
char ip6_src[BUFF_SIZE_IP6];
char ip6_dst[BUFF_SIZE_IP6];
inet_ntop(AF_INET6, &ip6_h->ip6_src, ip6_src, BUFF_SIZE_IP6);
inet_ntop(AF_INET6, &ip6_h->ip6_dst, ip6_dst, BUFF_SIZE_IP6);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Flow[0x%08x] Payload len[%u] Next hdr[%u:%s] "
"Hop limit[%u] Source[%s] Destination[%s]",
ntohl(ip6_h->ip6_flow), ntohs(ip6_h->ip6_plen),
}
}
-static void __pcap_ip_info(const u_char *packet)
+static void __pcap_ip_info(const u_char **packet)
{
- ip_t *ip_h = (ip_t *)(packet + SIZE_ETHER_HEADER);
+ ip_t *ip_h = (ip_t *)*packet;
char ip_src[BUFF_SIZE_IP];
char ip_dst[BUFF_SIZE_IP];
inet_ntop(AF_INET, &ip_h->ip_src, ip_src, BUFF_SIZE_IP);
inet_ntop(AF_INET, &ip_h->ip_dst, ip_dst, BUFF_SIZE_IP);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Header len[%u] TOS[0x%02x] Total len[%u] "
"ID[0x%04x] Flags[0x%02x] TTL[%u] Protocol[%u:%s] "
"Checksum[0x%04x] Source[%s] Destination[%s]",
__pcap_ip_protocol_info(ip_h->ip_p),
ntohs(ip_h->ip_sum), ip_src, ip_dst);
+ *packet += SIZE_IP_HEADER;
+
switch (ip_h->ip_p) {
case IPPROTO_ICMP:
__pcap_icmp_info(packet);
}
}
-static void __pcap_eth_info(const u_char *packet)
+static void __pcap_eth_info(const u_char **packet)
{
- eth_t *eth_h = (eth_t *)packet;
+ eth_t *eth_h = (eth_t *)*packet;
u_int8_t *eth_shost = eth_h->ether_shost;
u_int8_t *eth_dhost = eth_h->ether_dhost;
char shost[BUFF_SIZE_HOST];
ether_type = ntohs(eth_h->ether_type);
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Source[%s] Destination[%s] Type[0x%04x:%s]",
shost, dhost, ether_type, __pcap_eth_type_info(ether_type));
+
+ *packet += SIZE_ETHER_HEADER;
+}
+
+static const char *__pcap_family_info(u_int8_t family)
+{
+ char *info = NULL;
+
+ switch (family) {
+ case AF_INET:
+ info = "IPv4";
+ break;
+ case AF_INET6:
+ info = "IPv6";
+ break;
+ default:
+ info = "Unknown";
+ break;
+ }
+
+ return info;
+}
+
+static const char *__pcap_tlv_type_info(u_int16_t type)
+{
+ char *info = NULL;
+
+ switch (type) {
+ case NFULA_PACKET_HDR:
+ info = "NFULA_PACKET_HDR";
+ break;
+ case NFULA_MARK:
+ info = "NFULA_MARK";
+ break;
+ case NFULA_TIMESTAMP:
+ info = "NFULA_TIMESTAMP";
+ break;
+ case NFULA_IFINDEX_INDEV:
+ info = "NFULA_IFINDEX_INDEV";
+ break;
+ case NFULA_IFINDEX_OUTDEV:
+ info = "NFULA_IFINDEX_OUTDEV";
+ break;
+ case NFULA_IFINDEX_PHYSINDEV:
+ info = "NFULA_IFINDEX_PHYSINDEV";
+ break;
+ case NFULA_IFINDEX_PHYSOUTDEV:
+ info = "NFULA_IFINDEX_PHYSOUTDEV";
+ break;
+ case NFULA_HWADDR:
+ info = "NFULA_HWADDR";
+ break;
+ case NFULA_PAYLOAD:
+ info = "NFULA_PAYLOAD";
+ break;
+ case NFULA_PREFIX:
+ info = "NFULA_PREFIX";
+ break;
+ case NFULA_UID:
+ info = "NFULA_UID";
+ break;
+ case NFULA_SEQ:
+ info = "NFULA_SEQ";
+ break;
+ case NFULA_SEQ_GLOBAL:
+ info = "NFULA_SEQ_GLOBAL";
+ break;
+ case NFULA_GID:
+ info = "NFULA_GID";
+ break;
+ case NFULA_HWTYPE:
+ info = "NFULA_HWTYPE";
+ break;
+ case NFULA_HWHEADER:
+ info = "NFULA_HWHEADER";
+ break;
+ case NFULA_HWLEN:
+ info = "NFULA_HWLEN";
+ break;
+ default:
+ info = "Unknown";
+ break;
+ }
+
+ return info;
+}
+
+static void __pcap_nflog_tlv_info(const u_char **packet,
+ u_int32_t length, u_int32_t caplen)
+{
+ nflog_tlv_t *tlv_h;
+ u_int16_t tlv_length;
+ u_int16_t tlv_type;
+ GString *value;
+ u_int16_t value_len;
+ u_char *value_pos = NULL;
+ gchar *value_str = NULL;
+
+ length -= SIZE_NFLOG_HDR;
+ caplen -= SIZE_NFLOG_HDR;
+
+ while (length > 0) {
+ if (caplen < SIZE_NFLOG_TLV || length < SIZE_NFLOG_TLV)
+ break;
+
+ tlv_h = (nflog_tlv_t *)*packet;
+ tlv_length = tlv_h->tlv_length;
+ if (tlv_length % 4 != 0)
+ tlv_length += 4 - tlv_length % 4;
+ tlv_type = tlv_h->tlv_type;
+
+ if (tlv_length < SIZE_NFLOG_TLV)
+ break;
+
+ if (caplen < tlv_length || length < tlv_length)
+ break;
+
+ if (STC_PCAP_LOG) {
+ if (tlv_type != NFULA_PAYLOAD) {
+ nflog_hwaddr_t *hwaddr;
+ nflog_timestamp_s *timestamp;
+ char host[BUFF_SIZE_HOST];
+ u_int32_t sec;
+ int len = 0;
+ char *time = NULL;
+
+ switch (tlv_type) {
+ case NFULA_HWADDR:
+ hwaddr = (nflog_hwaddr_t *)((u_char *)tlv_h + SIZE_NFLOG_TLV);
+ g_strlcpy(host,
+ ether_ntoa((const struct ether_addr *)hwaddr->hw_addr),
+ sizeof(host));
+ STC_LOGD("Type[%s:%u] Length[%u] Hwaddr[%s]",
+ __pcap_tlv_type_info(tlv_type), tlv_type,
+ tlv_h->tlv_length, host);
+ break;
+ case NFULA_TIMESTAMP:
+ timestamp = (nflog_timestamp_s *)((u_char *)tlv_h + SIZE_NFLOG_TLV);
+ sec = ntohl(timestamp->ts[1]);
+ time = ctime((const time_t *)&sec);
+ len = strlen(time);
+ time[len - 1] = '\0';
+
+ STC_LOGD("Type[%s:%u] Length[%u] Timestamp[%s]",
+ __pcap_tlv_type_info(tlv_type), tlv_type,
+ tlv_h->tlv_length, time);
+ break;
+ case NFULA_PREFIX:
+ value_len = tlv_h->tlv_length - SIZE_NFLOG_TLV;
+ value = g_string_sized_new(value_len);
+ if (value) {
+ value_pos = (u_char *)tlv_h + SIZE_NFLOG_TLV;
+ while (value_len--)
+ g_string_append_printf(value, "%c", *(value_pos++));
+ value_str = g_string_free(value, FALSE);
+ }
+
+ STC_LOGD("Type[%s:%u] Length[%u] Prefix[%s]",
+ __pcap_tlv_type_info(tlv_type), tlv_type,
+ tlv_h->tlv_length, value_str);
+
+ FREE(value_str);
+ break;
+ default:
+ value_len = tlv_h->tlv_length - SIZE_NFLOG_TLV;
+ value = g_string_sized_new(value_len);
+ if (value) {
+ value_pos = (u_char *)tlv_h + SIZE_NFLOG_TLV;
+ while (value_len--)
+ g_string_append_printf(value, "%02x", *(value_pos++));
+ value_str = g_string_free(value, FALSE);
+ }
+
+ STC_LOGD("Type[%s:%u] Length[%u] Value[%s]",
+ __pcap_tlv_type_info(tlv_type), tlv_type,
+ tlv_h->tlv_length, value_str);
+
+ FREE(value_str);
+ break;
+ }
+ } else {
+ STC_LOGD("Type[%s:%u] Length[%u]",
+ __pcap_tlv_type_info(tlv_type),
+ tlv_type, tlv_h->tlv_length);
+ }
+ }
+
+ if (tlv_type == NFULA_PAYLOAD) {
+ *packet += SIZE_NFLOG_TLV;
+ break;
+ }
+
+ *packet += tlv_length;
+ length -= tlv_length;
+ caplen -= tlv_length;
+ }
+}
+
+static void __pcap_nflog_hdr_info(const u_char **packet)
+{
+ nflog_hdr_t *hdr_h = (nflog_hdr_t *)*packet;
+ u_int8_t family = hdr_h->nflog_family;
+ u_int8_t version = hdr_h->nflog_version;
+ u_int16_t resource_id = ntohs(hdr_h->nflog_rid);
+
+ if (STC_PCAP_LOG)
+ STC_LOGD("Family[%s:%u] Version[%u] Resource id[%u]",
+ __pcap_family_info(family), family, version, resource_id);
+
+ *packet += SIZE_NFLOG_HDR;
}
static void __pcap_fm_info(const struct pcap_pkthdr *pkthdr)
int len = 0;
struct timeval ts = pkthdr->ts;
__time_t tv_sec = ts.tv_sec;
- __suseconds_t tv_usec = tv_usec;
+ __suseconds_t tv_usec = ts.tv_usec;
if (g_pcap_start_fm == false) {
g_pcap_tv = ts;
len = strlen(curr);
curr[len - 1] = '\0';
- if (STC_DEBUG_LOG && STC_PCAP_LOG)
+ if (STC_PCAP_LOG)
STC_LOGD("Arrival time[%s] Timeval[%.06f] "
"Frame len[%u] Capture len[%u]", curr,
(float)((tv_sec - g_pcap_tv.tv_sec) * 1000000 +
static void __pcap_handler(u_char *param,
const struct pcap_pkthdr *pkthdr,
const u_char *packet) {
- eth_t *eth_h;
- unsigned short eth_type;
/* int len = pkthdr->len; */
+ stc_pcap_data_s *pcap_data = (stc_pcap_data_s *)param;
+ eth_t *eth_h;
+ u_int16_t eth_type;
+ nflog_hdr_t *nflog_h;
+ u_int8_t nflog_family;
__pcap_fm_info(pkthdr);
- eth_h = (eth_t *)packet;
- __pcap_eth_info(packet);
+ switch (pcap_data->encap_type) {
+ case ENCAPTYPE_ETHERNET:
+ eth_h = (eth_t *)packet;
+ eth_type = ntohs(eth_h->ether_type);
- eth_type = ntohs(eth_h->ether_type);
- switch (eth_type) {
- case ETHERTYPE_IP:
- __pcap_ip_info(packet);
- /* __pcap_data_info(pcaket, len); */
- break;
- case ETHERTYPE_IPV6:
- __pcap_ipv6_info(packet);
- break;
- case ETHERTYPE_ARP:
- case ETHERTYPE_REVARP:
- __pcap_arp_info(packet);
+ __pcap_eth_info(&packet);
+
+ switch (eth_type) {
+ case ETHERTYPE_IP:
+ __pcap_ip_info(&packet);
+ /* __pcap_data_info(pcaket, len); */
+ break;
+ case ETHERTYPE_IPV6:
+ __pcap_ipv6_info(&packet);
+ break;
+ case ETHERTYPE_ARP:
+ case ETHERTYPE_REVARP:
+ __pcap_arp_info(&packet);
+ break;
+ case ETHERTYPE_LOOPBACK:
+ break;
+ default:
+ break;
+ }
break;
- case ETHERTYPE_LOOPBACK:
+ case ENCAPTYPE_NFLOG:
+ nflog_h = (nflog_hdr_t *)packet;
+ nflog_family = nflog_h->nflog_family;
+
+ __pcap_nflog_hdr_info(&packet);
+ __pcap_nflog_tlv_info(&packet, pkthdr->len, pkthdr->caplen);
+
+ switch (nflog_family) {
+ case AF_INET:
+ __pcap_ip_info(&packet);
+ break;
+ case AF_INET6:
+ __pcap_ipv6_info(&packet);
+ break;
+ default:
+ break;
+ }
break;
default:
break;
if (g_pcap_tables == NULL)
return false;
- snprintf(buf, sizeof(buf), "%s_%d",
+ snprintf(buf, sizeof(buf), "%s:%d",
pcap_data->ifname, pcap_data->nflog_group);
lookup = g_hash_table_lookup(g_pcap_tables, buf);
for (dev = alldevs; dev; dev = dev->next) {
if (g_strcmp0(dev->name, pcap_data->ifname) == 0) {
- name = g_strdup(dev->name);
+ if (g_strcmp0(dev->name, NFLOG_IFNAME) == 0) {
+ name = g_strdup(pcap_data->nfname);
+ pcap_data->encap_type = ENCAPTYPE_NFLOG;
+ } else {
+ name = g_strdup(pcap_data->ifname);
+ pcap_data->encap_type = ENCAPTYPE_ETHERNET;
+ }
break;
}
}
goto thread_exit;
}
+ STC_LOGD("Pcap open live [%p]", pcap_data->handle);
+
STC_LOGD("Pcap loop start [%s]", name);
- pcap_loop(pcap_data->handle, 0, __pcap_handler, NULL);
+ pcap_loop(pcap_data->handle, 0, __pcap_handler, (u_char *)pcap_data);
STC_LOGD("Pcap loop end [%s]", name);
pcap_close(pcap_data->handle);
- STC_LOGD("Pcap closed [%s]", name);
+ STC_LOGD("Pcap closed [%p]", pcap_data->handle);
thread_exit:
FREE(name);
STC_ERROR_FAIL,
"Invalid parameter [ifname]");
- snprintf(buf, sizeof(buf), "%s_%d", ifname, nflog_group);
+ snprintf(buf, sizeof(buf), "%s:%d", ifname, nflog_group);
lookup = g_hash_table_lookup(g_pcap_tables, buf);
if (lookup) {
}
data->ifname = g_strdup(ifname);
+ data->nfname = g_strdup(buf);
data->nflog_group = nflog_group;
data->thread = g_thread_new(buf, __pcap_thread_func, data);
STC_ERROR_FAIL,
"Invalid parameter [ifname]");
- snprintf(buf, sizeof(buf), "%s_%d", ifname, nflog_group);
+ snprintf(buf, sizeof(buf), "%s:%d", ifname, nflog_group);
lookup = g_hash_table_lookup(g_pcap_tables, buf);
if (!lookup) {