]> git.stg.codes - stg.git/blobdiff - projects/stargazer/plugins/capture/cap_nf/cap_nf.cpp
Implemented NFQ capturing.
[stg.git] / projects / stargazer / plugins / capture / cap_nf / cap_nf.cpp
index a572e8a17af9efc02ab86c8c28e11a79a20302ea..8c4fdc2dd350cf9dbc9306d59273cf39446d2366 100644 (file)
@@ -39,13 +39,18 @@ $Author: faust $
 
 #include <vector>
 
-#include "stg/common.h" 
+#include "stg/common.h"
 #include "stg/raw_ip_packet.h"
 #include "stg/traffcounter.h"
 #include "stg/plugin_creator.h"
 #include "cap_nf.h"
 
+namespace
+{
 PLUGIN_CREATOR<NF_CAP> cnc;
+}
+
+extern "C" PLUGIN * GetPlugin();
 
 PLUGIN * GetPlugin()
 {
@@ -54,8 +59,9 @@ return cnc.GetPlugin();
 
 NF_CAP::NF_CAP()
     : traffCnt(NULL),
-      tidTCP(0),
-      tidUDP(0),
+      settings(),
+      tidTCP(),
+      tidUDP(),
       runningTCP(false),
       runningUDP(false),
       stoppedTCP(true),
@@ -63,7 +69,9 @@ NF_CAP::NF_CAP()
       portT(0),
       portU(0),
       sockTCP(-1),
-      sockUDP(-1)
+      sockUDP(-1),
+      errorStr(),
+      logger(GetPluginLogger(GetStgLogger(), "cap_nf"))
 {
 }
 
@@ -115,6 +123,7 @@ if (portU > 0)
         runningUDP = false;
         CloseUDP();
         errorStr = "Cannot create UDP thread";
+        logger("Cannot create UDP thread.");
         printfd(__FILE__, "Error: Cannot create UDP thread\n");
         return -1;
         }
@@ -130,6 +139,7 @@ if (portT > 0)
         {
         runningTCP = false;
         CloseTCP();
+        logger("Cannot create TCP thread.");
         errorStr = "Cannot create TCP thread";
         printfd(__FILE__, "Error: Cannot create TCP thread\n");
         return -1;
@@ -146,7 +156,8 @@ if (portU && !stoppedUDP)
     CloseUDP();
     for (int i = 0; i < 25 && !stoppedUDP; ++i)
         {
-        usleep(200000);
+        struct timespec ts = {0, 200000000};
+        nanosleep(&ts, NULL);
         }
     if (stoppedUDP)
         {
@@ -157,10 +168,12 @@ if (portU && !stoppedUDP)
         if (pthread_kill(tidUDP, SIGUSR1))
             {
             errorStr = "Error sending signal to UDP thread";
+            logger("Error sending sugnal to UDP thread.");
             printfd(__FILE__, "Error: Error sending signal to UDP thread\n");
             return -1;
             }
         printfd(__FILE__, "UDP thread NOT stopped\n");
+        logger("Cannot stop UDP thread.");
         }
     }
 if (portT && !stoppedTCP)
@@ -168,7 +181,8 @@ if (portT && !stoppedTCP)
     CloseTCP();
     for (int i = 0; i < 25 && !stoppedTCP; ++i)
         {
-        usleep(200000);
+        struct timespec ts = {0, 200000000};
+        nanosleep(&ts, NULL);
         }
     if (stoppedTCP)
         {
@@ -179,10 +193,12 @@ if (portT && !stoppedTCP)
         if (pthread_kill(tidTCP, SIGUSR1))
             {
             errorStr = "Error sending signal to TCP thread";
+            logger("Error sending signal to TCP thread.");
             printfd(__FILE__, "Error: Error sending signal to TCP thread\n");
             return -1;
             }
         printfd(__FILE__, "TCP thread NOT stopped\n");
+        logger("Cannot stop TCP thread.");
         }
     }
 return 0;
@@ -195,6 +211,7 @@ sockUDP = socket(PF_INET, SOCK_DGRAM, 0);
 if (sockUDP <= 0)
     {
     errorStr = "Error opening UDP socket";
+    logger("Cannot create UDP socket: %s", strerror(errno));
     printfd(__FILE__, "Error: Error opening UDP socket\n");
     return true;
     }
@@ -204,6 +221,7 @@ sin.sin_addr.s_addr = inet_addr("0.0.0.0");
 if (bind(sockUDP, (struct sockaddr *)&sin, sizeof(sin)))
     {
     errorStr = "Error binding UDP socket";
+    logger("Cannot bind UDP socket: %s", strerror(errno));
     printfd(__FILE__, "Error: Error binding UDP socket\n");
     return true;
     }
@@ -217,6 +235,7 @@ sockTCP = socket(PF_INET, SOCK_STREAM, 0);
 if (sockTCP <= 0)
     {
     errorStr = "Error opening TCP socket";
+    logger("Cannot create TCP socket: %s", strerror(errno));
     printfd(__FILE__, "Error: Error opening TCP socket\n");
     return true;
     }
@@ -226,12 +245,14 @@ sin.sin_addr.s_addr = inet_addr("0.0.0.0");
 if (bind(sockTCP, (struct sockaddr *)&sin, sizeof(sin)))
     {
     errorStr = "Error binding TCP socket";
+    logger("Cannot bind TCP socket: %s", strerror(errno));
     printfd(__FILE__, "Error: Error binding TCP socket\n");
     return true;
     }
 if (listen(sockTCP, 1))
     {
     errorStr = "Error listening on TCP socket";
+    logger("Cannot listen on TCP socket: %s", strerror(errno));
     printfd(__FILE__, "Error: Error listening TCP socket\n");
     return true;
     }
@@ -240,11 +261,11 @@ return false;
 
 void * NF_CAP::RunUDP(void * c)
 {
+sigset_t signalSet;
+sigfillset(&signalSet);
+pthread_sigmask(SIG_BLOCK, &signalSet, NULL);
+
 NF_CAP * cap = static_cast<NF_CAP *>(c);
-uint8_t buf[BUF_SIZE];
-int res;
-struct sockaddr_in sin;
-socklen_t slen;
 cap->stoppedUDP = false;
 while (cap->runningUDP)
     {
@@ -254,11 +275,19 @@ while (cap->runningUDP)
         }
 
     // Data
-    slen = sizeof(sin);
-    res = recvfrom(cap->sockUDP, buf, BUF_SIZE, 0, reinterpret_cast<struct sockaddr *>(&sin), &slen);
+    struct sockaddr_in sin;
+    socklen_t slen = sizeof(sin);
+    uint8_t buf[BUF_SIZE];
+    ssize_t res = recvfrom(cap->sockUDP, buf, BUF_SIZE, 0, reinterpret_cast<struct sockaddr *>(&sin), &slen);
     if (!cap->runningUDP)
         break;
 
+    if (res < 0)
+        {
+        cap->logger("recvfrom error: %s", strerror(errno));
+        continue;
+        }
+
     if (res == 0) // EOF
         {
         continue;
@@ -282,12 +311,11 @@ return NULL;
 
 void * NF_CAP::RunTCP(void * c)
 {
+sigset_t signalSet;
+sigfillset(&signalSet);
+pthread_sigmask(SIG_BLOCK, &signalSet, NULL);
+
 NF_CAP * cap = static_cast<NF_CAP *>(c);
-uint8_t buf[BUF_SIZE];
-int res;
-int sd;
-struct sockaddr_in sin;
-socklen_t slen;
 cap->stoppedTCP = false;
 while (cap->runningTCP)
     {
@@ -297,18 +325,16 @@ while (cap->runningTCP)
         }
 
     // Data
-    slen = sizeof(sin);
-    sd = accept(cap->sockTCP, reinterpret_cast<struct sockaddr *>(&sin), &slen);
+    struct sockaddr_in sin;
+    socklen_t slen = sizeof(sin);
+    int sd = accept(cap->sockTCP, reinterpret_cast<struct sockaddr *>(&sin), &slen);
     if (!cap->runningTCP)
         break;
 
     if (sd <= 0)
         {
-        if (errno != EINTR)
-            {
-            cap->errorStr = "Error accepting connection";
-            printfd(__FILE__, "Error: Error accepting connection\n");
-            }
+        if (sd < 0)
+            cap->logger("accept error: %s", strerror(errno));
         continue;
         }
 
@@ -318,7 +344,12 @@ while (cap->runningTCP)
         continue;
         }
 
-    res = recv(sd, buf, BUF_SIZE, MSG_WAITALL);
+    uint8_t buf[BUF_SIZE];
+    ssize_t res = recv(sd, buf, BUF_SIZE, MSG_WAITALL);
+
+    if (res < 0)
+        cap->logger("recv error: %s", strerror(errno));
+
     close(sd);
 
     if (!cap->runningTCP)
@@ -333,11 +364,6 @@ while (cap->runningTCP)
     // Need to check actual data length and wait all data to receive
     if (res < 24)
         {
-        if (errno != EINTR)
-            {
-            cap->errorStr = "Invalid data received";
-            printfd(__FILE__, "Error: Invalid data received through TCP\n");
-            }
         continue;
         }
 
@@ -347,7 +373,7 @@ cap->stoppedTCP = true;
 return NULL;
 }
 
-void NF_CAP::ParseBuffer(uint8_t * buf, int size)
+void NF_CAP::ParseBuffer(uint8_t * buf, ssize_t size)
 {
 RAW_PACKET ip;
 NF_HEADER * hdr = reinterpret_cast<NF_HEADER *>(buf);
@@ -373,14 +399,14 @@ for (int i = 0; i < packets; ++i)
     {
     NF_DATA * data = reinterpret_cast<NF_DATA *>(buf + 24 + i * 48);
 
-    ip.header.ipHeader.ip_v = 4;
-    ip.header.ipHeader.ip_hl = 5;
-    ip.header.ipHeader.ip_p = data->proto;
+    ip.rawPacket.header.ipHeader.ip_v = 4;
+    ip.rawPacket.header.ipHeader.ip_hl = 5;
+    ip.rawPacket.header.ipHeader.ip_p = data->proto;
     ip.dataLen = ntohl(data->octets);
-    ip.header.ipHeader.ip_src.s_addr = data->srcAddr;
-    ip.header.ipHeader.ip_dst.s_addr = data->dstAddr;
-    ip.header.sPort = data->srcPort;
-    ip.header.dPort = data->dstPort;
+    ip.rawPacket.header.ipHeader.ip_src.s_addr = data->srcAddr;
+    ip.rawPacket.header.ipHeader.ip_dst.s_addr = data->dstAddr;
+    ip.rawPacket.header.sPort = data->srcPort;
+    ip.rawPacket.header.dPort = data->dstPort;
 
     traffCnt->Process(ip);
     }