suricata
source-ipfw.c
Go to the documentation of this file.
1 /* Copyright (C) 2007-2014 Open Information Security Foundation
2  *
3  * You can copy, redistribute or modify this Program under the terms of
4  * the GNU General Public License version 2 as published by the Free
5  * Software Foundation.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * version 2 along with this program; if not, write to the Free Software
14  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
15  * 02110-1301, USA.
16  */
17 
18 /**
19  * \file
20  *
21  * \author Nick Rogness <nick@rogness.net>
22  * \author Eric Leblond <eric@regit.org>
23  *
24  * IPFW packet acquisition support
25  */
26 
27 #include "suricata-common.h"
28 #include "suricata.h"
29 #include "decode.h"
30 #include "packet.h"
31 #include "packet-queue.h"
32 #include "threads.h"
33 #include "threadvars.h"
34 #include "tm-queuehandlers.h"
35 #include "tm-threads.h"
36 #include "source-ipfw.h"
37 #include "util-debug.h"
38 #include "conf.h"
39 #include "util-byte.h"
40 #include "util-privs.h"
41 #include "util-datalink.h"
42 #include "util-device-private.h"
43 #include "runmodes.h"
44 
45 #ifndef IPFW
46 /* Handle the case if --enable-ipfw was not used
47  *
48  */
49 
50 TmEcode NoIPFWSupportExit(ThreadVars *, const void *, void **);
51 
53 {
54 
55  tmm_modules[TMM_RECEIVEIPFW].name = "ReceiveIPFW";
56  tmm_modules[TMM_RECEIVEIPFW].ThreadInit = NoIPFWSupportExit;
61 }
62 
64 {
65  tmm_modules[TMM_VERDICTIPFW].name = "VerdictIPFW";
66  tmm_modules[TMM_VERDICTIPFW].ThreadInit = NoIPFWSupportExit;
71 }
72 
74 {
75  tmm_modules[TMM_DECODEIPFW].name = "DecodeIPFW";
76  tmm_modules[TMM_DECODEIPFW].ThreadInit = NoIPFWSupportExit;
82 }
83 
84 TmEcode NoIPFWSupportExit(ThreadVars *tv, const void *initdata, void **data)
85 {
86 
87  SCLogError("Error creating thread %s: you do not have support for ipfw "
88  "enabled please recompile with --enable-ipfw",
89  tv->name);
90  exit(EXIT_FAILURE);
91 }
92 
93 #else /* We have IPFW compiled in */
94 
95 #include "action-globals.h"
96 
97 #define IPFW_ACCEPT 0
98 #define IPFW_DROP 1
99 
100 #define IPFW_SOCKET_POLL_MSEC 300
101 
102 extern uint32_t max_pending_packets;
103 
104 /**
105  * \brief Structure to hold thread specific variables.
106  */
107 typedef struct IPFWThreadVars_
108 {
109  /* data link type for the thread, probably not needed */
110  int datalink;
111 
112  /* this one should be not changing after init */
113  uint16_t port_num;
114  /* position into the NFQ queue var array */
115  uint16_t ipfw_index;
116 
117  /* counters */
118  uint32_t pkts;
119  uint64_t bytes;
120  uint32_t errs;
121  uint32_t accepted;
122  uint32_t dropped;
124 
125 static IPFWThreadVars ipfw_t[IPFW_MAX_QUEUE];
126 static IPFWQueueVars ipfw_q[IPFW_MAX_QUEUE];
127 static uint16_t receive_port_num = 0;
128 static SCMutex ipfw_init_lock;
129 
130 /* IPFW Prototypes */
131 static void *IPFWGetQueue(int number);
132 static TmEcode ReceiveIPFWThreadInit(ThreadVars *, const void *, void **);
133 static TmEcode ReceiveIPFWLoop(ThreadVars *tv, void *data, void *slot);
134 static void ReceiveIPFWThreadExitStats(ThreadVars *, void *);
135 static TmEcode ReceiveIPFWThreadDeinit(ThreadVars *, void *);
136 
137 static TmEcode IPFWSetVerdict(ThreadVars *, IPFWThreadVars *, Packet *);
138 static TmEcode VerdictIPFW(ThreadVars *, Packet *, void *);
139 static TmEcode VerdictIPFWThreadInit(ThreadVars *, const void *, void **);
140 static void VerdictIPFWThreadExitStats(ThreadVars *, void *);
141 static TmEcode VerdictIPFWThreadDeinit(ThreadVars *, void *);
142 
143 static TmEcode DecodeIPFWThreadInit(ThreadVars *, const void *, void **);
144 static TmEcode DecodeIPFWThreadDeinit(ThreadVars *tv, void *data);
145 static TmEcode DecodeIPFW(ThreadVars *, Packet *, void *);
146 
147 /**
148  * \brief Registration Function for RecieveIPFW.
149  * \todo Unit tests are needed for this module.
150  */
152 {
153  SCMutexInit(&ipfw_init_lock, NULL);
154 
155  tmm_modules[TMM_RECEIVEIPFW].name = "ReceiveIPFW";
156  tmm_modules[TMM_RECEIVEIPFW].ThreadInit = ReceiveIPFWThreadInit;
158  tmm_modules[TMM_RECEIVEIPFW].PktAcqLoop = ReceiveIPFWLoop;
160  tmm_modules[TMM_RECEIVEIPFW].ThreadExitPrintStats = ReceiveIPFWThreadExitStats;
161  tmm_modules[TMM_RECEIVEIPFW].ThreadDeinit = ReceiveIPFWThreadDeinit;
164  SC_CAP_NET_BROADCAST; /** \todo untested */
166 }
167 
168 /**
169  * \brief Registration Function for VerdictIPFW.
170  * \todo Unit tests are needed for this module.
171  */
173 {
174  tmm_modules[TMM_VERDICTIPFW].name = "VerdictIPFW";
175  tmm_modules[TMM_VERDICTIPFW].ThreadInit = VerdictIPFWThreadInit;
176  tmm_modules[TMM_VERDICTIPFW].Func = VerdictIPFW;
177  tmm_modules[TMM_VERDICTIPFW].ThreadExitPrintStats = VerdictIPFWThreadExitStats;
178  tmm_modules[TMM_VERDICTIPFW].ThreadDeinit = VerdictIPFWThreadDeinit;
180  SC_CAP_NET_BIND_SERVICE; /** \todo untested */
182 }
183 
184 /**
185  * \brief Registration Function for DecodeIPFW.
186  * \todo Unit tests are needed for this module.
187  */
189 {
190  tmm_modules[TMM_DECODEIPFW].name = "DecodeIPFW";
191  tmm_modules[TMM_DECODEIPFW].ThreadInit = DecodeIPFWThreadInit;
192  tmm_modules[TMM_DECODEIPFW].Func = DecodeIPFW;
194  tmm_modules[TMM_DECODEIPFW].ThreadDeinit = DecodeIPFWThreadDeinit;
196 }
197 
198 static inline void IPFWMutexInit(IPFWQueueVars *nq)
199 {
200  char *active_runmode = RunmodeGetActive();
201 
202  if (active_runmode && !strcmp("workers", active_runmode)) {
203  nq->use_mutex = 0;
204  SCLogInfo("IPFW running in 'workers' runmode, will not use mutex.");
205  } else {
206  nq->use_mutex = 1;
207  }
208  if (nq->use_mutex)
209  SCMutexInit(&nq->socket_lock, NULL);
210 }
211 
212 static inline void IPFWMutexLock(IPFWQueueVars *nq)
213 {
214  if (nq->use_mutex)
215  SCMutexLock(&nq->socket_lock);
216 }
217 
218 static inline void IPFWMutexUnlock(IPFWQueueVars *nq)
219 {
220  if (nq->use_mutex)
222 }
223 
224 #ifndef IP_MAXPACKET
225 #define IP_MAXPACKET 65535
226 #endif
227 
228 TmEcode ReceiveIPFWLoop(ThreadVars *tv, void *data, void *slot)
229 {
230  SCEnter();
231 
232  IPFWThreadVars *ptv = (IPFWThreadVars *)data;
233  IPFWQueueVars *nq = NULL;
234  uint8_t pkt[IP_MAXPACKET];
235  int pktlen=0;
236  struct pollfd IPFWpoll;
237  struct timeval IPFWts;
238  Packet *p = NULL;
239 
240  nq = IPFWGetQueue(ptv->ipfw_index);
241  if (nq == NULL) {
242  SCLogWarning("Can't get thread variable");
244  }
245 
246  SCLogInfo("Thread '%s' will run on port %d (item %d)",
247  tv->name, nq->port_num, ptv->ipfw_index);
248 
249  // Indicate that the thread is actually running its application level code (i.e., it can poll
250  // packets)
252 
253  while (1) {
254  if (unlikely(suricata_ctl_flags != 0)) {
256  }
257 
258  IPFWpoll.fd = nq->fd;
259  IPFWpoll.events = POLLRDNORM;
260  /* Poll the socket for status */
261  if ( (poll(&IPFWpoll, 1, IPFW_SOCKET_POLL_MSEC)) > 0) {
262  if (!(IPFWpoll.revents & (POLLRDNORM | POLLERR)))
263  continue;
264  }
265 
266  if ((pktlen = recvfrom(nq->fd, pkt, sizeof(pkt), 0,
267  (struct sockaddr *)&nq->ipfw_sin,
268  &nq->ipfw_sinlen)) == -1) {
269  /* We received an error on socket read */
270  if (errno == EINTR || errno == EWOULDBLOCK) {
271  /* Nothing for us to process */
272  continue;
273  } else {
274  SCLogWarning("Read from IPFW divert socket failed: %s", strerror(errno));
276  }
277  }
278  /* We have a packet to process */
279  memset (&IPFWts, 0, sizeof(struct timeval));
280  gettimeofday(&IPFWts, NULL);
281 
282  /* make sure we have at least one packet in the packet pool, to prevent
283  * us from alloc'ing packets at line rate */
284  PacketPoolWait();
285 
287  if (p == NULL) {
289  }
291 
292  SCLogDebug("Received Packet Len: %d", pktlen);
293 
294  p->ts = SCTIME_FROM_TIMEVAL(&IPFWts);
295 
296  ptv->pkts++;
297  ptv->bytes += pktlen;
298 
299  p->datalink = ptv->datalink;
300 
301  p->ipfw_v.ipfw_index = ptv->ipfw_index;
302 
303  PacketCopyData(p, pkt, pktlen);
304  SCLogDebug("Packet info: pkt_len: %" PRIu32 " (pkt %02x, pkt_data %02x)",
305  GET_PKT_LEN(p), *pkt, *(GET_PKT_DATA(p)));
306 
307  if (TmThreadsSlotProcessPkt(tv, ((TmSlot *) slot)->slot_next, p)
308  != TM_ECODE_OK) {
310  }
311 
313  }
314 
316 }
317 
318 /**
319  * \brief Init function for RecieveIPFW.
320  *
321  * This is a setup function for receiving packets
322  * via ipfw divert, binds a socket, and prepares to
323  * to read from it.
324  *
325  * \param tv pointer to ThreadVars
326  * \param initdata pointer to the divert port passed from the user
327  * \param data pointer gets populated with IPFWThreadVars
328  *
329  */
330 TmEcode ReceiveIPFWThreadInit(ThreadVars *tv, const void *initdata, void **data)
331 {
332  struct timeval timev;
333  IPFWThreadVars *ntv = (IPFWThreadVars *) initdata;
334  IPFWQueueVars *nq = IPFWGetQueue(ntv->ipfw_index);
335 
336  sigset_t sigs;
337  sigfillset(&sigs);
338  pthread_sigmask(SIG_UNBLOCK, &sigs, NULL);
339 
340  SCEnter();
341 
342  IPFWMutexInit(nq);
343  /* We need a divert socket to play with */
344 #ifdef PF_DIVERT
345  if ((nq->fd = socket(PF_DIVERT, SOCK_RAW, 0)) == -1) {
346 #else
347  if ((nq->fd = socket(PF_INET, SOCK_RAW, IPPROTO_DIVERT)) == -1) {
348 #endif
349  SCLogError("Can't create divert socket: %s", strerror(errno));
351  }
352 
353  /* set a timeout to the socket so we can check for a signal
354  * in case we don't get packets for a longer period. */
355  timev.tv_sec = 1;
356  timev.tv_usec = 0;
357 
358  if (setsockopt(nq->fd, SOL_SOCKET, SO_RCVTIMEO, &timev, sizeof(timev)) == -1) {
359  SCLogError("Can't set IPFW divert socket timeout: %s", strerror(errno));
361  }
362 
363  nq->ipfw_sinlen=sizeof(nq->ipfw_sin);
364  memset(&nq->ipfw_sin, 0, nq->ipfw_sinlen);
365  nq->ipfw_sin.sin_family = PF_INET;
366  nq->ipfw_sin.sin_addr.s_addr = INADDR_ANY;
367  nq->ipfw_sin.sin_port = htons(nq->port_num);
368 
369  /* Bind that SOB */
370  if (bind(nq->fd, (struct sockaddr *)&nq->ipfw_sin, nq->ipfw_sinlen) == -1) {
371  SCLogError("Can't bind divert socket on port %d: %s", nq->port_num, strerror(errno));
373  }
374 
375  ntv->datalink = DLT_RAW;
377 
378  *data = (void *)ntv;
379 
381 }
382 
383 /**
384  * \brief This function prints stats to the screen at exit.
385  * \todo Unit tests are needed for this module.
386  * \param tv pointer to ThreadVars
387  * \param data pointer that gets cast into IPFWThreadVars for ptv
388  */
389 void ReceiveIPFWThreadExitStats(ThreadVars *tv, void *data)
390 {
391  IPFWThreadVars *ptv = (IPFWThreadVars *)data;
392 
393  SCEnter();
394 
395  SCLogNotice("(%s) Treated: Pkts %" PRIu32 ", Bytes %" PRIu64 ", Errors %" PRIu32 "",
396  tv->name, ptv->pkts, ptv->bytes, ptv->errs);
397  SCLogNotice("(%s) Verdict: Accepted %"PRIu32", Dropped %"PRIu32 "",
398  tv->name, ptv->accepted, ptv->dropped);
399 
400 
401  SCReturn;
402 }
403 
404 /**
405  * \brief DeInit function closes divert socket at exit.
406  * \todo Unit tests are needed for this module.
407  * \param tv pointer to ThreadVars
408  * \param data pointer that gets cast into IPFWThreadVars for ptv
409  */
410 TmEcode ReceiveIPFWThreadDeinit(ThreadVars *tv, void *data)
411 {
412  IPFWThreadVars *ptv = (IPFWThreadVars *)data;
413  IPFWQueueVars *nq = IPFWGetQueue(ptv->ipfw_index);
414 
415  SCEnter();
416 
417  if (close(nq->fd) < 0) {
418  SCLogWarning("Unable to disable ipfw socket: %s", strerror(errno));
420  }
421 
423 }
424 
425 /**
426  * \brief This function passes off to link type decoders.
427  * \todo Unit tests are needed for this module.
428  *
429  * DecodeIPFW decodes packets from IPFW and passes
430  * them off to the proper link type decoder.
431  *
432  * \param tv pointer to ThreadVars
433  * \param p pointer to the current packet
434  * \param data pointer that gets cast into IPFWThreadVars for ptv
435  */
436 TmEcode DecodeIPFW(ThreadVars *tv, Packet *p, void *data)
437 {
438  IPV4Hdr *ip4h = (IPV4Hdr *)GET_PKT_DATA(p);
439  IPV6Hdr *ip6h = (IPV6Hdr *)GET_PKT_DATA(p);
441 
442  SCEnter();
443 
445 
446  /* update counters */
448 
449  /* Process IP packets */
450  if (IPV4_GET_RAW_VER(ip4h) == 4) {
451  if (unlikely(GET_PKT_LEN(p) > USHRT_MAX)) {
452  return TM_ECODE_FAILED;
453  }
454  SCLogDebug("DecodeIPFW ip4 processing");
456 
457  } else if(IPV6_GET_RAW_VER(ip6h) == 6) {
458  if (unlikely(GET_PKT_LEN(p) > USHRT_MAX)) {
459  return TM_ECODE_FAILED;
460  }
461  SCLogDebug("DecodeIPFW ip6 processing");
463 
464  } else {
465  /* We don't support anything besides IP packets for now, bridged packets? */
466  SCLogInfo("IPFW unknown protocol support %02x", *GET_PKT_DATA(p));
468  }
469 
471 
473 }
474 
475 /**
476  * \brief This function initializes the DecodeThreadVariables
477  *
478  *
479  * \param tv pointer to ThreadVars
480  * \param initdata pointer for passing in args
481  * \param data pointer that gets cast into IPFWThreadVars for ptv
482  */
483 TmEcode DecodeIPFWThreadInit(ThreadVars *tv, const void *initdata, void **data)
484 {
485  DecodeThreadVars *dtv = NULL;
487 
488  if (dtv == NULL)
490 
492 
493  *data = (void *)dtv;
494 
496 }
497 
498 TmEcode DecodeIPFWThreadDeinit(ThreadVars *tv, void *data)
499 {
500  if (data != NULL)
501  DecodeThreadVarsFree(tv, data);
503 }
504 
505 /**
506  * \brief This function sets the Verdict and processes the packet
507  *
508  *
509  * \param tv pointer to ThreadVars
510  * \param p pointer to the Packet
511  */
512 TmEcode IPFWSetVerdict(ThreadVars *tv, IPFWThreadVars *ptv, Packet *p)
513 {
514  uint32_t verdict;
515 #if 0
516  struct pollfd IPFWpoll;
517 #endif
518  IPFWQueueVars *nq = NULL;
519 
520  SCEnter();
521 
522  if (p == NULL) {
523  SCLogWarning("Packet is NULL");
525  }
526 
527  nq = IPFWGetQueue(p->ipfw_v.ipfw_index);
528  if (nq == NULL) {
529  SCLogWarning("No thread found");
531  }
532 
533 #if 0
534  IPFWpoll.fd = nq->fd;
535  IPFWpoll.events = POLLWRNORM;
536 #endif
537 
538  if (PacketCheckAction(p, ACTION_DROP)) {
539  verdict = IPFW_DROP;
540  } else {
541  verdict = IPFW_ACCEPT;
542  }
543 
544  if (verdict == IPFW_ACCEPT) {
545  SCLogDebug("IPFW Verdict is to Accept");
546  ptv->accepted++;
547 
548  /* For divert sockets, accepting means writing the
549  * packet back to the socket for ipfw to pick up
550  */
551  SCLogDebug("IPFWSetVerdict writing to socket %d, %p, %u", nq->fd, GET_PKT_DATA(p),GET_PKT_LEN(p));
552 
553 #if 0
554  while ((poll(&IPFWpoll,1,IPFW_SOCKET_POLL_MSEC)) < 1) {
555  /* Did we receive a signal to shutdown */
557  SCLogInfo("Received ThreadShutdown: IPFW divert socket writing interrupted");
559  }
560  }
561 #endif
562 
563  IPFWMutexLock(nq);
564  if (sendto(nq->fd, GET_PKT_DATA(p), GET_PKT_LEN(p), 0,(struct sockaddr *)&nq->ipfw_sin, nq->ipfw_sinlen) == -1) {
565  int r = errno;
566  switch (r) {
567  default:
568  SCLogWarning("Write to ipfw divert socket failed: %s", strerror(r));
569  IPFWMutexUnlock(nq);
571  case EHOSTDOWN:
572  case ENETDOWN:
573  break;
574  }
575  }
576 
577  IPFWMutexUnlock(nq);
578 
579  SCLogDebug("Sent Packet back into IPFW Len: %d",GET_PKT_LEN(p));
580 
581  } /* end IPFW_ACCEPT */
582 
583 
584  if (verdict == IPFW_DROP) {
585  SCLogDebug("IPFW SetVerdict is to DROP");
586  ptv->dropped++;
587 
588  /** \todo For divert sockets, dropping means not writing the packet back to the socket.
589  * Need to see if there is some better way to free the packet from the queue */
590 
591  } /* end IPFW_DROP */
592 
594 }
595 
596 
597 /**
598  * \brief This function handles the Verdict processing
599  * \todo Unit tests are needed for this module.
600  *
601  *
602  * \param tv pointer to ThreadVars
603  * \param p pointer to the Packet
604  * \param data pointer that gets cast into IPFWThreadVars for ptv
605  */
606 TmEcode VerdictIPFW(ThreadVars *tv, Packet *p, void *data)
607 {
608  IPFWThreadVars *ptv = (IPFWThreadVars *)data;
609  TmEcode retval = TM_ECODE_OK;
610 
611  SCEnter();
612 
613  /* can't verdict a "fake" packet */
614  if (p->flags & PKT_PSEUDO_STREAM_END) {
616  }
617 
618  /* This came from NFQ.
619  * If this is a tunnel packet we check if we are ready to verdict already. */
620  if (PacketIsTunnel(p)) {
621  bool verdict = VerdictTunnelPacket(p);
622 
623  /* don't verdict if we are not ready */
624  if (verdict) {
625  SCLogDebug("Setting verdict on tunnel");
626  retval = IPFWSetVerdict(tv, ptv, p->root ? p->root : p);
627  }
628  } else {
629  /* no tunnel, verdict normally */
630  SCLogDebug("Setting verdict on non-tunnel");
631  retval = IPFWSetVerdict(tv, ptv, p);
632  }
633 
634  SCReturnInt(retval);
635 }
636 
637 /**
638  * \brief This function initializes the VerdictThread
639  *
640  *
641  * \param t pointer to ThreadVars
642  * \param initdata pointer for passing in args
643  * \param data pointer that gets cast into IPFWThreadVars for ptv
644  */
645 TmEcode VerdictIPFWThreadInit(ThreadVars *tv, const void *initdata, void **data)
646 {
647 
648  IPFWThreadVars *ptv = NULL;
649 
650  SCEnter();
651 
652  /* Setup Thread vars */
653  if ((ptv = SCCalloc(1, sizeof(IPFWThreadVars))) == NULL)
655 
656  *data = (void *)ptv;
657 
659 }
660 
661 /**
662  * \brief This function deinitializes the VerdictThread
663  *
664  *
665  * \param tv pointer to ThreadVars
666  * \param data pointer that gets cast into IPFWThreadVars for ptv
667  */
668 TmEcode VerdictIPFWThreadDeinit(ThreadVars *tv, void *data)
669 {
670 
671  SCEnter();
672 
673  /* We don't need to do anything...not sure quite yet */
674 
675 
677 }
678 
679 /**
680  * \brief This function prints stats for the VerdictThread
681  *
682  *
683  * \param tv pointer to ThreadVars
684  * \param data pointer that gets cast into IPFWThreadVars for ptv
685  */
686 void VerdictIPFWThreadExitStats(ThreadVars *tv, void *data)
687 {
688  IPFWThreadVars *ptv = (IPFWThreadVars *)data;
689  SCLogInfo("IPFW Processing: - (%s) Pkts accepted %" PRIu32 ", dropped %" PRIu32 "", tv->name, ptv->accepted, ptv->dropped);
690 }
691 
692 /**
693  * \brief Add an IPFW divert
694  *
695  * \param string with the queue name
696  *
697  * \retval 0 on success.
698  * \retval -1 on failure.
699  */
700 int IPFWRegisterQueue(char *queue)
701 {
702  IPFWThreadVars *ntv = NULL;
703  IPFWQueueVars *nq = NULL;
704  /* Extract the queue number from the specified command line argument */
705  uint16_t port_num = 0;
706  if ((StringParseUint16(&port_num, 10, strlen(queue), queue)) < 0)
707  {
708  SCLogError("specified queue number %s is not "
709  "valid",
710  queue);
711  return -1;
712  }
713 
714  SCMutexLock(&ipfw_init_lock);
715  if (receive_port_num >= IPFW_MAX_QUEUE) {
716  SCLogError("too much IPFW divert port registered (%d)", receive_port_num);
717  SCMutexUnlock(&ipfw_init_lock);
718  return -1;
719  }
720  if (receive_port_num == 0) {
721  memset(&ipfw_t, 0, sizeof(ipfw_t));
722  memset(&ipfw_q, 0, sizeof(ipfw_q));
723  }
724 
725  ntv = &ipfw_t[receive_port_num];
726  ntv->ipfw_index = receive_port_num;
727 
728  nq = &ipfw_q[receive_port_num];
729  nq->port_num = port_num;
730  receive_port_num++;
731  SCMutexUnlock(&ipfw_init_lock);
732  LiveRegisterDeviceName(queue);
733 
734  SCLogDebug("Queue \"%s\" registered.", queue);
735  return 0;
736 }
737 
738 /**
739  * \brief Get a pointer to the IPFW queue at index
740  *
741  * \param number idx of the queue in our array
742  *
743  * \retval ptr pointer to the IPFWThreadVars at index
744  * \retval NULL on error
745  */
746 void *IPFWGetQueue(int number)
747 {
748  if (number >= receive_port_num)
749  return NULL;
750 
751  return (void *)&ipfw_q[number];
752 }
753 
754 /**
755  * \brief Get a pointer to the IPFW thread at index
756  *
757  * This function is temporary used as configuration parser.
758  *
759  * \param number idx of the queue in our array
760  *
761  * \retval ptr pointer to the IPFWThreadVars at index
762  * \retval NULL on error
763  */
764 void *IPFWGetThread(int number)
765 {
766  if (number >= receive_port_num)
767  return NULL;
768 
769  return (void *)&ipfw_t[number];
770 }
771 
772 #endif /* End ifdef IPFW */
773 
774 /* eof */
775 
TmModule_::cap_flags
uint8_t cap_flags
Definition: tm-modules.h:77
PacketCheckAction
bool PacketCheckAction(const Packet *p, const uint8_t a)
Definition: packet.c:49
util-device-private.h
util-byte.h
tm-threads.h
TmModuleReceiveIPFWRegister
void TmModuleReceiveIPFWRegister(void)
Registration Function for RecieveIPFW.
Definition: source-ipfw.c:151
IPFWQueueVars_::socket_lock
SCMutex socket_lock
Definition: source-ipfw.h:39
IPV6_GET_RAW_VER
#define IPV6_GET_RAW_VER(ip6h)
Definition: decode-ipv6.h:62
ThreadVars_::name
char name[16]
Definition: threadvars.h:65
TM_FLAG_VERDICT_TM
#define TM_FLAG_VERDICT_TM
Definition: tm-modules.h:35
PacketCopyData
int PacketCopyData(Packet *p, const uint8_t *pktdata, uint32_t pktlen)
Copy data to Packet payload and set packet length.
Definition: decode.c:377
PKT_IS_PSEUDOPKT
#define PKT_IS_PSEUDOPKT(p)
return 1 if the packet is a pseudo packet
Definition: decode.h:1319
unlikely
#define unlikely(expr)
Definition: util-optimize.h:35
IPFWThreadVars_::dropped
uint32_t dropped
Definition: source-ipfw.c:122
SCLogDebug
#define SCLogDebug(...)
Definition: util-debug.h:275
TmThreadsSetFlag
void TmThreadsSetFlag(ThreadVars *tv, uint32_t flag)
Set a thread flag.
Definition: tm-threads.c:101
action-globals.h
Packet_::flags
uint32_t flags
Definition: decode.h:544
threads.h
StringParseUint16
int StringParseUint16(uint16_t *res, int base, size_t len, const char *str)
Definition: util-byte.c:337
THV_RUNNING
#define THV_RUNNING
Definition: threadvars.h:55
Packet_::ipfw_v
IPFWPacketVars ipfw_v
Definition: decode.h:566
packet-queue.h
SCMutexLock
#define SCMutexLock(mut)
Definition: threads-debug.h:117
util-privs.h
SC_CAP_NET_BROADCAST
#define SC_CAP_NET_BROADCAST
Definition: util-privs.h:34
PacketDecodeFinalize
void PacketDecodeFinalize(ThreadVars *tv, DecodeThreadVars *dtv, Packet *p)
Finalize decoding of a packet.
Definition: decode.c:232
RunmodeGetActive
char * RunmodeGetActive(void)
Definition: runmodes.c:199
TM_ECODE_FAILED
@ TM_ECODE_FAILED
Definition: tm-threads-common.h:82
IPFW_MAX_QUEUE
#define IPFW_MAX_QUEUE
Definition: source-ipfw.h:28
THV_PAUSE
#define THV_PAUSE
Definition: threadvars.h:38
IPFW_DROP
#define IPFW_DROP
Definition: source-ipfw.c:98
TmModule_::PktAcqLoop
TmEcode(* PktAcqLoop)(ThreadVars *, void *, void *)
Definition: tm-modules.h:58
TM_ECODE_OK
@ TM_ECODE_OK
Definition: tm-threads-common.h:81
TmModule_::ThreadDeinit
TmEcode(* ThreadDeinit)(ThreadVars *, void *)
Definition: tm-modules.h:53
PKT_SET_SRC
#define PKT_SET_SRC(p, src_val)
Definition: decode.h:1323
SC_CAP_NET_BIND_SERVICE
#define SC_CAP_NET_BIND_SERVICE
Definition: util-privs.h:33
DecodeRegisterPerfCounters
void DecodeRegisterPerfCounters(DecodeThreadVars *dtv, ThreadVars *tv)
Definition: decode.c:628
IPFWThreadVars_::accepted
uint32_t accepted
Definition: source-ipfw.c:121
decode.h
util-debug.h
PKT_SRC_WIRE
@ PKT_SRC_WIRE
Definition: decode.h:52
TmModule_::PktAcqBreakLoop
TmEcode(* PktAcqBreakLoop)(ThreadVars *, void *)
Definition: tm-modules.h:61
IPFWQueueVars_::fd
int fd
Definition: source-ipfw.h:38
SCMutexUnlock
#define SCMutexUnlock(mut)
Definition: threads-debug.h:119
PKT_PSEUDO_STREAM_END
#define PKT_PSEUDO_STREAM_END
Definition: decode.h:1266
TmModuleVerdictIPFWRegister
void TmModuleVerdictIPFWRegister(void)
Registration Function for VerdictIPFW.
Definition: source-ipfw.c:172
SCEnter
#define SCEnter(...)
Definition: util-debug.h:277
GET_PKT_DATA
#define GET_PKT_DATA(p)
Definition: decode.h:209
ThreadVars_
Per thread variable structure.
Definition: threadvars.h:58
SCTIME_FROM_TIMEVAL
#define SCTIME_FROM_TIMEVAL(tv)
Definition: util-time.h:79
IPFWThreadVars_::errs
uint32_t errs
Definition: source-ipfw.c:120
TmModule_::Func
TmEcode(* Func)(ThreadVars *, Packet *, void *)
Definition: tm-modules.h:56
THV_KILL
#define THV_KILL
Definition: threadvars.h:40
SCLogWarning
#define SCLogWarning(...)
Macro used to log WARNING messages.
Definition: util-debug.h:255
SC_CAP_NET_ADMIN
#define SC_CAP_NET_ADMIN
Definition: util-privs.h:31
BUG_ON
#define BUG_ON(x)
Definition: suricata-common.h:317
IPFWRegisterQueue
int IPFWRegisterQueue(char *queue)
Add an IPFW divert.
Definition: source-ipfw.c:700
IPFWQueueVars_::ipfw_sin
struct sockaddr_in ipfw_sin
Definition: source-ipfw.h:45
PacketPoolWait
void PacketPoolWait(void)
Definition: tmqh-packetpool.c:80
SCReturn
#define SCReturn
Definition: util-debug.h:279
IPV6Hdr_
Definition: decode-ipv6.h:32
Packet_
Definition: decode.h:501
TM_FLAG_DECODE_TM
#define TM_FLAG_DECODE_TM
Definition: tm-modules.h:33
tmm_modules
TmModule tmm_modules[TMM_SIZE]
Definition: tm-modules.c:29
DecodeIPV6
int DecodeIPV6(ThreadVars *tv, DecodeThreadVars *dtv, Packet *p, const uint8_t *pkt, uint16_t len)
Definition: decode-ipv6.c:560
GET_PKT_LEN
#define GET_PKT_LEN(p)
Definition: decode.h:208
conf.h
source-ipfw.h
IPV4_GET_RAW_VER
#define IPV4_GET_RAW_VER(ip4h)
Definition: decode-ipv4.h:95
TmSlot_
Definition: tm-threads.h:53
TmEcode
TmEcode
Definition: tm-threads-common.h:80
max_pending_packets
uint32_t max_pending_packets
Definition: suricata.c:183
IPFWThreadVars_::ipfw_index
uint16_t ipfw_index
Definition: source-ipfw.c:115
IPFWThreadVars
struct IPFWThreadVars_ IPFWThreadVars
Structure to hold thread specific variables.
TmModule_::name
const char * name
Definition: tm-modules.h:48
runmodes.h
SCLogInfo
#define SCLogInfo(...)
Macro used to log INFORMATIONAL messages.
Definition: util-debug.h:225
SCMutexInit
#define SCMutexInit(mut, mutattrs)
Definition: threads-debug.h:116
TM_FLAG_RECEIVE_TM
#define TM_FLAG_RECEIVE_TM
Definition: tm-modules.h:32
dtv
DecodeThreadVars * dtv
Definition: fuzz_decodepcapfile.c:33
IP_MAXPACKET
#define IP_MAXPACKET
Definition: source-ipfw.c:225
IPV4Hdr_
Definition: decode-ipv4.h:72
tm-queuehandlers.h
IPFWQueueVars_::use_mutex
uint8_t use_mutex
Definition: source-ipfw.h:40
IPFWThreadVars_
Structure to hold thread specific variables.
Definition: source-ipfw.c:108
DecodeThreadVarsFree
void DecodeThreadVarsFree(ThreadVars *tv, DecodeThreadVars *dtv)
Definition: decode.c:820
IPFW_SOCKET_POLL_MSEC
#define IPFW_SOCKET_POLL_MSEC
Definition: source-ipfw.c:100
suricata-common.h
IPFWGetThread
void * IPFWGetThread(int number)
Get a pointer to the IPFW thread at index.
Definition: source-ipfw.c:764
IPFW_ACCEPT
#define IPFW_ACCEPT
Definition: source-ipfw.c:97
packet.h
ACTION_DROP
#define ACTION_DROP
Definition: action-globals.h:30
IPFWThreadVars_::pkts
uint32_t pkts
Definition: source-ipfw.c:118
TmModule_::ThreadInit
TmEcode(* ThreadInit)(ThreadVars *, const void *, void **)
Definition: tm-modules.h:51
IPFWThreadVars_::datalink
int datalink
Definition: source-ipfw.c:110
TMM_RECEIVEIPFW
@ TMM_RECEIVEIPFW
Definition: tm-threads-common.h:47
tv
ThreadVars * tv
Definition: fuzz_decodepcapfile.c:32
TMM_VERDICTIPFW
@ TMM_VERDICTIPFW
Definition: tm-threads-common.h:46
TmModule_::ThreadExitPrintStats
void(* ThreadExitPrintStats)(ThreadVars *, void *)
Definition: tm-modules.h:52
threadvars.h
TmModuleDecodeIPFWRegister
void TmModuleDecodeIPFWRegister(void)
Registration Function for DecodeIPFW.
Definition: source-ipfw.c:188
Packet_::root
struct Packet_ * root
Definition: decode.h:653
SCLogError
#define SCLogError(...)
Macro used to log ERROR messages.
Definition: util-debug.h:267
IPFWQueueVars_::port_num
uint16_t port_num
Definition: source-ipfw.h:42
DecodeThreadVars_
Structure to hold thread specific data for all decode modules.
Definition: decode.h:963
DecodeThreadVarsAlloc
DecodeThreadVars * DecodeThreadVarsAlloc(ThreadVars *tv)
Alloc and setup DecodeThreadVars.
Definition: decode.c:802
IPFWQueueVars_::ipfw_sinlen
socklen_t ipfw_sinlen
Definition: source-ipfw.h:46
IPFWThreadVars_::bytes
uint64_t bytes
Definition: source-ipfw.c:119
suricata.h
IPFWPacketVars_::ipfw_index
int ipfw_index
Definition: source-ipfw.h:33
TMM_DECODEIPFW
@ TMM_DECODEIPFW
Definition: tm-threads-common.h:45
IPFWQueueVars_
Definition: source-ipfw.h:37
StatsSyncCountersIfSignalled
void StatsSyncCountersIfSignalled(ThreadVars *tv)
Definition: counters.c:450
LiveRegisterDeviceName
int LiveRegisterDeviceName(const char *dev)
Add a device for monitoring.
Definition: util-device.c:103
TmThreadsCheckFlag
int TmThreadsCheckFlag(ThreadVars *tv, uint32_t flag)
Check if a thread flag is set.
Definition: tm-threads.c:93
DecodeIPV4
int DecodeIPV4(ThreadVars *tv, DecodeThreadVars *dtv, Packet *p, const uint8_t *pkt, uint16_t len)
Definition: decode-ipv4.c:520
SCLogNotice
#define SCLogNotice(...)
Macro used to log NOTICE messages.
Definition: util-debug.h:243
SCCalloc
#define SCCalloc(nm, sz)
Definition: util-mem.h:53
SCReturnInt
#define SCReturnInt(x)
Definition: util-debug.h:281
SCMutex
#define SCMutex
Definition: threads-debug.h:114
IPFWThreadVars_::port_num
uint16_t port_num
Definition: source-ipfw.c:113
PacketGetFromQueueOrAlloc
Packet * PacketGetFromQueueOrAlloc(void)
Get a packet. We try to get a packet from the packetpool first, but if that is empty we alloc a packe...
Definition: decode.c:293
SC_CAP_NET_RAW
#define SC_CAP_NET_RAW
Definition: util-privs.h:32
TmModule_::flags
uint8_t flags
Definition: tm-modules.h:80
DecodeUpdatePacketCounters
void DecodeUpdatePacketCounters(ThreadVars *tv, const DecodeThreadVars *dtv, const Packet *p)
Definition: decode.c:768
suricata_ctl_flags
volatile uint8_t suricata_ctl_flags
Definition: suricata.c:172