NFQ inline changes

- split NFQRecvPkt into a Linux and Windows version for readability
- Add many function header comments
- convert tabs to spaces in Windows code.
remotes/origin/master-1.0.x
Victor Julien 16 years ago
parent 366671a8ce
commit 591c898f6a

@ -1,10 +1,16 @@
/* Copyright (c) 2008 Victor Julien <victor@inliniac.net> */
/* TODO
* - test if Receive and Verdict if both are present
/**
* \file
*
* \brief Netfilter's netfilter_queue support for reading packets from the
* kernel and setting verdicts back to it (inline mode).
*
* Supported on Linux and Windows.
*
* \todo test if Receive and Verdict if both are present
*
* \author Victor Julien <victor@inliniac.net>
*/
#include "suricata-common.h"
@ -289,11 +295,12 @@ TmEcode NFQInitThread(NFQThreadVars *nfq_t, uint16_t queue_num, uint32_t queue_m
SCLogDebug("nfq_t->h %p, nfq_t->nh %p, nfq_t->qh %p, nfq_t->fd %" PRId32 "",
nfq_t->h, nfq_t->nh, nfq_t->qh, nfq_t->fd);
#else /* OS_WIN32 */
SCMutexInit(&nfq_t->mutex_qh, NULL);
nfq_t->ovr.hEvent = CreateEvent(NULL, FALSE, FALSE, NULL);
nfq_t->fd = nfq_fd(nfq_t->h);
SCMutexInit(&nfq_t->mutex_qh, NULL);
nfq_t->ovr.hEvent = CreateEvent(NULL, FALSE, FALSE, NULL);
nfq_t->fd = nfq_fd(nfq_t->h);
SCLogDebug("nfq_t->h %p, nfq_t->qh %p, nfq_t->fd %p", nfq_t->h, nfq_t->qh, nfq_t->fd);
#endif /* OS_WIN32 */
return TM_ECODE_OK;
}
@ -360,53 +367,85 @@ TmEcode VerdictNFQThreadDeinit(ThreadVars *tv, void *data) {
return TM_ECODE_OK;
}
/**
* \brief NFQ function to get a packet from the kernel
*
* \note separate functions for Linux and Win32 for readability.
*/
#ifndef OS_WIN32
void NFQRecvPkt(NFQThreadVars *t) {
int rv, ret;
char buf[70000];
#ifdef OS_WIN32
static int timeouted = 0;
/* XXX what happens on rv == 0? */
rv = recv(t->fd, buf, sizeof(buf), 0);
if (rv < 0) {
if (errno == EINTR || errno == EWOULDBLOCK
) {
/* no error on timeout */
} else {
#ifdef COUNTERS
t->errs++;
#endif /* COUNTERS */
}
} else if(rv == 0) {
SCLogWarning(SC_ERR_NFQ_RECV, "recv got returncode 0");
} else {
#ifdef DBG_PERF
if (rv > t->dbg_maxreadsize)
t->dbg_maxreadsize = rv;
#endif /* DBG_PERF */
//printf("NFQRecvPkt: t %p, rv = %" PRId32 "\n", t, rv);
if (timeouted) {
if (WaitForSingleObject(t->ovr.hEvent, 1000) == WAIT_TIMEOUT) {
rv = -1;
errno = EINTR;
goto process_rv;
}
timeouted = 0;
}
SCMutexLock(&t->mutex_qh);
ret = nfq_handle_packet(t->h, buf, rv);
SCMutexUnlock(&t->mutex_qh);
if (ret != 0) {
SCLogWarning(SC_ERR_NFQ_HANDLE_PKT, "nfq_handle_packet error %" PRId32 "", ret);
}
}
}
#else /* WIN32 version of NFQRecvPkt */
void NFQRecvPkt(NFQThreadVars *t) {
int rv, ret;
char buf[70000];
static int timeouted = 0;
if (timeouted) {
if (WaitForSingleObject(t->ovr.hEvent, 1000) == WAIT_TIMEOUT) {
rv = -1;
errno = EINTR;
goto process_rv;
}
timeouted = 0;
}
read_packet_again:
if (!ReadFile(t->fd, buf, sizeof(buf), (DWORD*)&rv, &t->ovr)) {
if (GetLastError() != ERROR_IO_PENDING) {
rv = -1;
errno = EIO;
} else {
if (WaitForSingleObject(t->ovr.hEvent, 1000) == WAIT_TIMEOUT) {
rv = -1;
errno = EINTR;
timeouted = 1;
} else {
/* We needn't to call GetOverlappedResult() because it always fail with our error code ERROR_MORE_DATA. */
goto read_packet_again;
}
}
}
if (!ReadFile(t->fd, buf, sizeof(buf), (DWORD*)&rv, &t->ovr)) {
if (GetLastError() != ERROR_IO_PENDING) {
rv = -1;
errno = EIO;
} else {
if (WaitForSingleObject(t->ovr.hEvent, 1000) == WAIT_TIMEOUT) {
rv = -1;
errno = EINTR;
timeouted = 1;
} else {
/* We needn't to call GetOverlappedResult() because it always
* fail with our error code ERROR_MORE_DATA. */
goto read_packet_again;
}
}
}
process_rv:
#else /* OS_WIN32 */
/* XXX what happens on rv == 0? */
rv = recv(t->fd, buf, sizeof(buf), 0);
#endif /* OS_WIN32 */
if (rv < 0) {
if (errno == EINTR
#ifndef OS_WIN32
|| errno == EWOULDBLOCK
#endif
) {
if (errno == EINTR) {
/* no error on timeout */
} else {
#ifdef COUNTERS
@ -432,7 +471,11 @@ process_rv:
}
}
}
#endif /* OS_WIN32 */
/**
* \brief NFQ receive module main entry function: receive a packet from NFQ
*/
TmEcode ReceiveNFQ(ThreadVars *tv, Packet *p, void *data, PacketQueue *pq) {
NFQThreadVars *ntv = (NFQThreadVars *)data;
@ -451,6 +494,9 @@ TmEcode ReceiveNFQ(ThreadVars *tv, Packet *p, void *data, PacketQueue *pq) {
return TM_ECODE_OK;
}
/**
* \brief NFQ receive module stats printing function
*/
void ReceiveNFQThreadExitStats(ThreadVars *tv, void *data) {
NFQThreadVars *ntv = (NFQThreadVars *)data;
#ifdef COUNTERS
@ -459,6 +505,9 @@ void ReceiveNFQThreadExitStats(ThreadVars *tv, void *data) {
#endif
}
/**
* \brief NFQ verdict module stats printing function
*/
void VerdictNFQThreadExitStats(ThreadVars *tv, void *data) {
NFQThreadVars *ntv = (NFQThreadVars *)data;
#ifdef COUNTERS
@ -467,6 +516,9 @@ void VerdictNFQThreadExitStats(ThreadVars *tv, void *data) {
#endif
}
/**
* \brief NFQ verdict function
*/
void NFQSetVerdict(NFQThreadVars *t, Packet *p) {
int ret;
uint32_t verdict;
@ -495,6 +547,9 @@ void NFQSetVerdict(NFQThreadVars *t, Packet *p) {
}
}
/**
* \brief NFQ verdict module packet entry function
*/
TmEcode VerdictNFQ(ThreadVars *tv, Packet *p, void *data, PacketQueue *pq) {
NFQThreadVars *ntv = (NFQThreadVars *)data;
@ -528,10 +583,8 @@ TmEcode VerdictNFQ(ThreadVars *tv, Packet *p, void *data, PacketQueue *pq) {
return TM_ECODE_OK;
}
/*
*
*
*
/**
* \brief Decode a packet coming from NFQ
*/
TmEcode DecodeNFQ(ThreadVars *tv, Packet *p, void *data, PacketQueue *pq)
{
@ -561,6 +614,9 @@ TmEcode DecodeNFQ(ThreadVars *tv, Packet *p, void *data, PacketQueue *pq)
return TM_ECODE_OK;
}
/**
* \brief Initialize the NFQ Decode threadvars
*/
TmEcode DecodeNFQThreadInit(ThreadVars *tv, void *initdata, void **data)
{
DecodeThreadVars *dtv = NULL;

Loading…
Cancel
Save