Mixe for Privacy and Anonymity in the Internet
Classes | Macros | Typedefs | Functions
CAFirstMix.hpp File Reference
#include "doxygen.h"
#include "CAMix.hpp"
#include "CAMuxSocket.hpp"
#include "CAASymCipher.hpp"
#include "CAFirstMixChannelList.hpp"
#include "CAIPList.hpp"
#include "CASocketGroup.hpp"
#include "CAQueue.hpp"
#include "CAUtil.hpp"
#include "CAThread.hpp"
#include "CAThreadPool.hpp"
#include "TermsAndConditions.hpp"
#include "CALogPacketStats.hpp"
#include "CAConditionVariable.hpp"
#include "CATempIPBlockList.hpp"
#include "CASocketGroupEpoll.hpp"
#include "CAMixWithReplayDB.hpp"
#include "CAMutex.hpp"
Include dependency graph for CAFirstMix.hpp:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Classes

class  tUINT32withLock
 
struct  t_FirstMixChannelToQueueList_entry
 
class  CAFirstMixChannelToQueueList
 
class  CAFirstMix
 

Macros

#define TNC_SREQUEST   "TermsAndConditionsRequest"
 
#define TNC_RESPONSE   "TermsAndConditionsResponse"
 
#define TNC_SINTERRUPT   "TermsAndConditionsInterrupt"
 
#define TNC_REQ_TRANSLATION   "Translation"
 
#define TNC_RESOURCES   "Resources"
 
#define TNC_RESOURCE_TEMPLATE   "Template"
 
#define TNC_TEMPLATE_ROOT_ELEMENT   "TermsAndConditionsTemplate"
 
#define TNC_RESOURCE_CUSTOMIZED_SECT   "CustomizedSections"
 
#define TNC_RESPONSE_INVALID_REQUEST   "InvalidTermsAndConditionsRequest"
 
#define TNC_CONFIRM_REQ   "TermsAndConditionsConfirm"
 

Typedefs

typedef struct t_FirstMixChannelToQueueList_entry tFirstMixChannelToQueueListEntry
 

Functions

THREAD_RETURN fm_loopSendToMix (void *)
 How to end this thread: 0. More...
 
THREAD_RETURN fm_loopReadFromMix (void *)
 
THREAD_RETURN fm_loopAcceptUsers (void *)
 
THREAD_RETURN fm_loopReadFromUsers (void *)
 
THREAD_RETURN fm_loopDoUserLogin (void *param)
 
THREAD_RETURN fm_loopLog (void *)
 
THREAD_RETURN iplist_loopDoLogCountries (void *param)
 

Macro Definition Documentation

◆ TNC_CONFIRM_REQ

#define TNC_CONFIRM_REQ   "TermsAndConditionsConfirm"

Definition at line 69 of file CAFirstMix.hpp.

◆ TNC_REQ_TRANSLATION

#define TNC_REQ_TRANSLATION   "Translation"

Definition at line 62 of file CAFirstMix.hpp.

◆ TNC_RESOURCE_CUSTOMIZED_SECT

#define TNC_RESOURCE_CUSTOMIZED_SECT   "CustomizedSections"

Definition at line 66 of file CAFirstMix.hpp.

◆ TNC_RESOURCE_TEMPLATE

#define TNC_RESOURCE_TEMPLATE   "Template"

Definition at line 64 of file CAFirstMix.hpp.

◆ TNC_RESOURCES

#define TNC_RESOURCES   "Resources"

Definition at line 63 of file CAFirstMix.hpp.

◆ TNC_RESPONSE

#define TNC_RESPONSE   "TermsAndConditionsResponse"

Definition at line 60 of file CAFirstMix.hpp.

◆ TNC_RESPONSE_INVALID_REQUEST

#define TNC_RESPONSE_INVALID_REQUEST   "InvalidTermsAndConditionsRequest"

Definition at line 68 of file CAFirstMix.hpp.

◆ TNC_SINTERRUPT

#define TNC_SINTERRUPT   "TermsAndConditionsInterrupt"

Definition at line 61 of file CAFirstMix.hpp.

◆ TNC_SREQUEST

#define TNC_SREQUEST   "TermsAndConditionsRequest"

Definition at line 59 of file CAFirstMix.hpp.

◆ TNC_TEMPLATE_ROOT_ELEMENT

#define TNC_TEMPLATE_ROOT_ELEMENT   "TermsAndConditionsTemplate"

Definition at line 65 of file CAFirstMix.hpp.

Typedef Documentation

◆ tFirstMixChannelToQueueListEntry

Function Documentation

◆ fm_loopAcceptUsers()

THREAD_RETURN fm_loopAcceptUsers ( void *  param)

Definition at line 365 of file CAFirstMix.cpp.

1277  {
1278  INIT_STACK;
1279  BEGIN_STACK("CAFirstMix::fm_loopAcceptUsers");
1280  CAMsg::printMsg(LOG_DEBUG, "Start acceptusers\n");
1281 
1282  CAFirstMix* pFirstMix=(CAFirstMix*)param;
1283  CASocket** socketsIn=pFirstMix->m_arrSocketsIn;
1284  CAIPList* pIPList=pFirstMix->m_pIPList;
1285  CATempIPBlockList* pIPBlockList = pFirstMix->m_pIPBlockList;
1286  CAThreadPool* pthreadsLogin=pFirstMix->m_pthreadsLogin;
1287  UINT32 nSocketsIn=pFirstMix->m_nSocketsIn;
1288 #ifdef __BUILD_AS_SHADOW_PLUGIN__
1289  CASocketGroupEpoll* psocketgroupAccept=new CASocketGroupEpoll(false);
1290 #else
1291  CASocketGroup* psocketgroupAccept = new CASocketGroup(false);
1292 #endif
1293  CAMuxSocket* pNewMuxSocket;
1294  UINT8* peerIP=new UINT8[4];
1295  UINT32 i=0;
1296  SINT32 countRead;
1297  SINT32 ret;
1298  SINT32 retPeerIP = E_SUCCESS;
1299 
1300  pFirstMix->m_newConnections = 0;
1301 
1302  // kick out users that already have connected
1303  for(i=0;i<nSocketsIn;i++)
1304  {
1305  while (socketsIn[i]->close() != E_SUCCESS)
1306  {
1307  sSleep(1);
1308  }
1309  delete socketsIn[i];
1310  }
1311  CAMsg::printMsg(LOG_DEBUG, "Creating incoming sockets\n");
1312 
1313  if (CALibProxytest::getOptions()->createSockets(false,pFirstMix-> m_arrSocketsIn, pFirstMix->m_nSocketsIn) != E_SUCCESS)
1314  {
1315  goto END_THREAD;
1316  }
1317  CAMsg::printMsg(LOG_DEBUG, "Add sockets to select group\n");
1318  for(i=0;i<nSocketsIn;i++)
1319  {
1320  psocketgroupAccept->add(*socketsIn[i]);
1321  }
1322 #ifdef REPLAY_DETECTION //before we can start to accept users we have to ensure that we received the replay timestamps form the over mixes
1323  CAMsg::printMsg(LOG_DEBUG,"Waiting for Replay Timestamp from next mixes\n");
1324  i=0;
1325  while(!pFirstMix->m_bRestart && i < pFirstMix->m_u32MixCount-1)
1326  {
1327  if(pFirstMix->m_arMixParameters[i].m_u32ReplayOffset==0)//not set yet
1328  {
1329  msSleep(100);//wait a little bit and try again
1330  continue;
1331  }
1332  i++;
1333  }
1334  CAMsg::printMsg(LOG_DEBUG,"All Replay Timestamp received\n");
1335 #endif
1336  CAMsg::printMsg(LOG_DEBUG, "Start accept users inner loop\n");
1337 
1338  while(!pFirstMix->m_bRestart)
1339  {
1340  if (pIPBlockList->count()>40)
1341  {
1342  CAMsg::printMsg(LOG_DEBUG,"UserAcceptLoop: login timeout list counts %d. We have %d users, %d open sockets and %d new connections. Restarting server sockets...\n",pIPBlockList->count(), pFirstMix->getNrOfUsers() ,CASocket::countOpenSockets(), pFirstMix->m_newConnections);
1343  for(i=0;i<nSocketsIn;i++)
1344  {
1345  psocketgroupAccept->remove(*socketsIn[i]);
1346  while (socketsIn[i]->close() != E_SUCCESS)
1347  {
1348  sSleep(1);
1349  }
1350  }
1351 
1352  if (CALibProxytest::getOptions()->createSockets(false,pFirstMix-> m_arrSocketsIn, pFirstMix->m_nSocketsIn) != E_SUCCESS)
1353  {
1354  // could not listen
1355  goto END_THREAD;
1356  }
1357  for(i=0;i<nSocketsIn;i++)
1358  {
1359  psocketgroupAccept->add(*socketsIn[i]);
1360  }
1361  sSleep(1);
1362  }
1363 #ifdef __BUILD_AS_SHADOW_PLUGIN__
1364  CAMsg::printMsg(LOG_DEBUG, "Before acceptusers->select()\n");
1365  countRead=psocketgroupAccept->select();
1366  CAMsg::printMsg(LOG_DEBUG, "after acceptusers->select()\n");
1367 #else
1368  countRead = psocketgroupAccept->select(10000);
1369 #endif
1370  if(countRead<0)
1371  { //check for Error - are we restarting ?
1372  if(pFirstMix->m_bRestart ||countRead!=E_TIMEDOUT)
1373  goto END_THREAD;
1374  }
1375  i=0;
1376 #ifdef _DEBUG
1377  CAMsg::printMsg(LOG_DEBUG,"UserAcceptLoop: countRead=%i\n",countRead);
1378 #endif
1379  while(countRead>0&&i<nSocketsIn)
1380  {
1381  if(psocketgroupAccept->isSignaled(*socketsIn[i]))
1382  {
1383  countRead--;
1384  #ifdef _DEBUG
1385  CAMsg::printMsg(LOG_DEBUG,"New direct Connection from Client!\n");
1386  #endif
1387  #ifdef SYM_CHANNEL_CIPHER_CTR
1388  pNewMuxSocket=new CAMuxSocket(CTR);
1389  #elif defined NO_ENCRYPTION
1390  pNewMuxSocket = new CAMuxSocket(NULL_CIPHER);
1391 #else
1392  pNewMuxSocket=new CAMuxSocket(OFB);
1393  #endif
1394  ret=socketsIn[i]->accept(*(pNewMuxSocket->getCASocket()));
1395  pFirstMix->incNewConnections();
1396 
1397  if(ret!=E_SUCCESS)
1398  {
1399  // may return E_SOCKETCLOSED or E_SOCKET_LIMIT
1400  CAMsg::printMsg(LOG_ERR,"Accept Error %u - direct Connection from Client!\n",GET_NET_ERROR);
1401  }
1402  else if( (CALibProxytest::getOptions()->getMaxNrOfUsers() > 0 &&
1404  && (isAllowedToPassRestrictions(pNewMuxSocket->getCASocket()) != E_SUCCESS)
1405 
1406  )
1407  {
1408  CAMsg::printMsg(LOG_DEBUG,"CAFirstMix User control: Too many users (Maximum:%d)! Rejecting user...\n", pFirstMix->getNrOfUsers(),CALibProxytest::getOptions()->getMaxNrOfUsers());
1409  ret = E_UNKNOWN;
1410  }
1412  && (isAllowedToPassRestrictions(pNewMuxSocket->getCASocket()) != E_SUCCESS)
1413  )
1414 
1415  {
1416  /* This should protect the mix from flooding attacks
1417  * No more than MAX_CONCURRENT_NEW_CONNECTIONS are allowed.
1418  */
1419 #ifdef _DEBUG
1420  CAMsg::printMsg(LOG_DEBUG,"CAFirstMix Flooding protection: Too many concurrent new connections (Maximum:%d)! Rejecting user...\n", CAFirstMix::MAX_CONCURRENT_NEW_CONNECTIONS);
1421 #endif
1422  ret = E_UNKNOWN;
1423  }
1424 //#ifndef PAYMENT
1425  else if ((ret = pNewMuxSocket->getCASocket()->getPeerIP(peerIP)) != E_SUCCESS ||
1426  (retPeerIP = pIPList->insertIP(peerIP)) < 0)
1427  // || (pIPBlockList->checkIP(peerIP) == E_UNKNOWN && isAllowedToPassRestrictions(pNewMuxSocket->getCASocket()) != E_SUCCESS))
1428  {
1429  if (ret != E_SUCCESS)
1430  {
1431  CAMsg::printMsg(LOG_DEBUG,"Could not insert IP address as IP could not be retrieved! We have %d login threads currently running.\n", pthreadsLogin->countRequests());
1432 
1433  }
1434  else if (retPeerIP < 0)
1435  {
1436  CAMsg::printMsg(LOG_DEBUG,"CAFirstMix Flooding protection: Could not insert IP address! We have %d login threads currently running.\n", pthreadsLogin->countRequests());
1437  pIPBlockList->insertIP(peerIP);
1438  }
1439  else if (pIPBlockList->checkIP(peerIP) == E_UNKNOWN)
1440  {
1441  CAMsg::printMsg(LOG_DEBUG, "Client IP address %u.%u.x.x is temporarily blocked! User login denied. We have %d open sockets and %d new connections.\n", peerIP[0],peerIP[1], CASocket::countOpenSockets(), pFirstMix->m_newConnections);
1442  pIPList->removeIP(peerIP);
1443  }
1444  ret = E_UNKNOWN;
1445  }
1446 //#endif
1447  else
1448  {
1450  d->pNewUser=pNewMuxSocket;
1451  d->pMix=pFirstMix;
1452  memcpy(d->peerIP,peerIP,4);
1453 #ifdef DEBUG
1454  CAMsg::printMsg(LOG_DEBUG,"%d concurrent client connections.\n", pFirstMix->m_newConnections);
1455 #endif
1456  if(pthreadsLogin->addRequest(fm_loopDoUserLogin,d)!=E_SUCCESS)
1457  {
1458  CAMsg::printMsg(LOG_ERR,"Could not add an login request to the login thread pool!\n");
1459  ret=E_UNKNOWN;
1460  }
1461  }
1462 
1463  if (ret != E_SUCCESS)
1464  {
1465  delete pNewMuxSocket;
1466  pNewMuxSocket = NULL;
1467  pFirstMix->decNewConnections();
1468  if(ret==E_SOCKETCLOSED&&pFirstMix->m_bRestart) //Hm, should we restart ??
1469  {
1470  goto END_THREAD;
1471  }
1472  else //if(ret==E_SOCKET_LIMIT) // Hm no free sockets - wait some time to hope to get a free one...
1473  {
1474  msSleep(400);
1475  }
1476  }
1477  }
1478  i++;
1479  }
1480  }
1481 END_THREAD:
1482  FINISH_STACK("CAFirstMix::fm_loopAcceptUsers");
1483 
1484  delete[] peerIP;
1485  peerIP = NULL;
1486  delete psocketgroupAccept;
1487  psocketgroupAccept = NULL;
1488 
1489  CAMsg::printMsg(LOG_DEBUG,"Exiting Thread AcceptUser\n");
1491  }
THREAD_RETURN fm_loopDoUserLogin(void *param)
struct T_UserLoginData t_UserLoginData
SINT32 isAllowedToPassRestrictions(CASocket *pNewMuxSocket)
@ NULL_CIPHER
#define INIT_STACK
Definition: CAThread.hpp:48
#define BEGIN_STACK(methodName)
Definition: CAThread.hpp:49
#define FINISH_STACK(methodName)
Definition: CAThread.hpp:50
SINT32 sSleep(UINT32 sec)
Sleeps sec Seconds.
Definition: CAUtil.cpp:425
SINT32 msSleep(UINT32 ms)
Sleeps ms milliseconds.
Definition: CAUtil.cpp:406
#define GET_NET_ERROR
Definition: StdAfx.h:469
#define THREAD_RETURN_SUCCESS
Definition: StdAfx.h:542
signed int SINT32
Definition: basetypedefs.h:132
unsigned char UINT8
Definition: basetypedefs.h:135
unsigned int UINT32
Definition: basetypedefs.h:131
UINT32 getMaxNrOfUsers()
CASocket ** m_arrSocketsIn
Definition: CAFirstMix.hpp:457
volatile bool m_bRestart
Definition: CAFirstMix.hpp:456
tMixParameters * m_arMixParameters
Definition: CAFirstMix.hpp:461
CAIPList * m_pIPList
Definition: CAFirstMix.hpp:446
volatile UINT32 m_newConnections
Definition: CAFirstMix.hpp:568
static const UINT32 MAX_CONCURRENT_NEW_CONNECTIONS
Definition: CAFirstMix.hpp:566
void incNewConnections()
Definition: CAFirstMix.hpp:571
CATempIPBlockList * m_pIPBlockList
Definition: CAFirstMix.hpp:447
void decNewConnections()
Definition: CAFirstMix.hpp:578
UINT32 m_nSocketsIn
Definition: CAFirstMix.hpp:455
CAThreadPool * m_pthreadsLogin
Definition: CAFirstMix.hpp:505
UINT32 getNrOfUsers()
The purpose of this class is to store a list of IP-Addresses.
Definition: CAIPList.hpp:62
SINT32 insertIP(const UINT8 ip[4])
Inserts the IP-Address into the list.
Definition: CAIPList.cpp:103
SINT32 removeIP(const UINT8 ip[4])
Removes the IP-Address from the list.
Definition: CAIPList.cpp:189
static CACmdLnOptions * getOptions()
static SINT32 printMsg(UINT32 typ, const char *format,...)
Writes a given message to the log.
Definition: CAMsg.cpp:251
CASocket * getCASocket()
Definition: CAMuxSocket.hpp:84
SINT32 remove(CASocket &s)
bool isSignaled(CASocket &s)
SINT32 add(CASocket &s)
Adds the socket s to the socket group.
virtual SINT32 getPeerIP(UINT8 ip[4])
Definition: CASocket.cpp:820
virtual SINT32 accept(CASocket &s)
Accepts a new connection.
Definition: CASocket.cpp:192
static UINT32 countOpenSockets()
Definition: CASocket.hpp:128
The purpose of this class is storing the IPs of JAP users who tried to hack/attack the payment system...
SINT32 insertIP(const UINT8 ip[4])
inserts an IP into the blocklist
SINT32 checkIP(const UINT8 ip[4])
check whether an IP is blocked
This class bla bla.
SINT32 addRequest(THREAD_MAIN_TYP, void *args)
Adds a new request (task) to this threadpool.
UINT32 countRequests()
#define E_SOCKETCLOSED
Definition: errorcodes.hpp:11
const SINT32 E_SUCCESS
Definition: errorcodes.hpp:2
#define E_UNKNOWN
Definition: errorcodes.hpp:3
#define E_TIMEDOUT
Definition: errorcodes.hpp:10
CAFirstMix * pMix
CAMuxSocket * pNewUser
UINT32 m_u32ReplayOffset
Definition: typedefs.hpp:218

◆ fm_loopDoUserLogin()

THREAD_RETURN fm_loopDoUserLogin ( void *  param)

Definition at line 367 of file CAFirstMix.cpp.

1550  {
1551  INIT_STACK;
1552  BEGIN_STACK("CAFirstMix::fm_loopDoUserLogin");
1553 #ifdef COUNTRY_STATS
1554  my_thread_init();
1555 #endif
1556 
1557  t_UserLoginData* d=(t_UserLoginData*)param;
1558  d->pMix->doUserLogin(d->pNewUser,d->peerIP);
1559 
1560  SAVE_STACK("CAFirstMix::fm_loopDoUserLogin", "after user login");
1561  d->pMix->decNewConnections();
1562  delete d;
1563  d = NULL;
1564 
1565 #ifdef COUNTRY_STATS
1566  my_thread_end();
1567 #endif
1568  FINISH_STACK("CAFirstMix::fm_loopDoUserLogin");
1569 
1571  }
#define SAVE_STACK(methodName, methodPosition)
Definition: CAThread.hpp:51
SINT32 doUserLogin(CAMuxSocket *pNewUSer, UINT8 perrIP[4])

◆ fm_loopLog()

THREAD_RETURN fm_loopLog ( void *  param)

Definition at line 551 of file CAFirstMix.cpp.

1495  {
1496  CAFirstMix* pFirstMix=(CAFirstMix*)param;
1497  pFirstMix->m_bRunLog=true;
1498  UINT32 countLog=0;
1499  while(pFirstMix->m_bRunLog)
1500  {
1501  if(countLog==0)
1502  {
1503  logMemoryUsage();
1504  countLog=10;
1505  }
1506  sSleep(30);
1507  countLog--;
1508  }
1510  }
void logMemoryUsage()
Log information about the current memory (heap) usage.
Definition: CAUtil.cpp:177
volatile bool m_bRunLog
Definition: CAFirstMix.hpp:552

◆ fm_loopReadFromMix()

THREAD_RETURN fm_loopReadFromMix ( void *  pParam)

ToDo: check if keep-alive is really correct here - should it not be moved upwards?

ToDo: check if keep-alive is really correct here - should it not be moved upwards?

Definition at line 364 of file CAFirstMix.cpp.

1093  {
1094  INIT_STACK;
1095  BEGIN_STACK("CAFirstMix::fm_loopReadFromMix");
1096 
1097  CAFirstMix* pFirstMix=(CAFirstMix*)pParam;
1098  CAMuxSocket* pMuxSocket=pFirstMix->m_pMuxOut;
1099  CAQueue* pQueue=pFirstMix->m_pQueueReadFromMix;
1100  tQueueEntry* pQueueEntry=new tQueueEntry;
1101  MIXPACKET* pMixPacket=&pQueueEntry->packet;
1102  CASingleSocketGroup* pSocketGroup=new CASingleSocketGroup(false);
1103  pSocketGroup->add(*pMuxSocket);
1104  #ifdef USE_POOL
1105  CAPool* pPool=new CAPool(MIX_POOL_SIZE);
1106  #endif
1107  UINT64 keepaliveNow,keepaliveLast;
1108  UINT32 u32KeepAliveRecvInterval=pFirstMix->m_u32KeepAliveRecvInterval;
1109  getcurrentTimeMillis(keepaliveLast);
1110  CAControlChannelDispatcher* pControlChannelDispatcher=pFirstMix->m_pMuxOutControlChannelDispatcher;
1111  while (!pFirstMix->m_bRestart)
1112  {
1114  {
1115 #ifdef DEBUG
1116  CAMsg::printMsg(LOG_DEBUG, "CAFirstMix::Queue is full!\n");
1117 #endif
1118  msSleep(200);
1119  getcurrentTimeMillis(keepaliveLast);
1120  continue;
1121  }
1122  //check if the connection is broken because we did not received a Keep_alive-Message
1123  getcurrentTimeMillis(keepaliveNow);
1124  UINT32 keepaliveDiff = diff64(keepaliveNow, keepaliveLast);
1125  if (keepaliveDiff > u32KeepAliveRecvInterval)
1126  {
1127  CAMsg::printMsg(LOG_DEBUG, "CAFirstMix::loopReadFromMix() -- restart because of KeepAlive-Traffic Timeout!\n");
1128  pFirstMix->m_bRestart = true;
1130  break;
1131  }
1132  SINT32 ret = pSocketGroup->select(MIX_POOL_TIMEOUT);
1133  if (ret < 0)
1134  {
1135  if (ret == E_TIMEDOUT)
1136  {
1137 #ifdef USE_POOL
1138  pMixPacket->flags=CHANNEL_DUMMY;
1139  pMixPacket->channel=DUMMY_CHANNEL;
1140  getRandom(pMixPacket->data,DATA_SIZE);
1141 #ifdef LOG_PACKET_TIMES
1142  setZero64(pQueueEntry->timestamp_proccessing_start);
1143 #endif
1144 #else
1145  continue;
1146 #endif
1147  }
1148  else
1149  {
1150  /* another error occured (happens sometimes while debugging because
1151  * of interruption, if a breakpoint is reached -> poll() returns
1152  * errorcode EINTR)
1153  * Note: Any Error on select() does not mean, that the underliny connections have some error state, because
1154  * in this case select() returns the socket and than this socket returns the error
1155  */
1156 #ifdef DEBUG
1157  CAMsg::printMsg(LOG_DEBUG, "CAFirstMix::loopReadFromMix() - socket select error: %i\n",ret);
1158 #endif
1159  continue;
1160  }
1161  }
1162  else if (ret > 0)
1163  {
1164  ret = pMuxSocket->receive(pMixPacket);
1165 #ifdef LOG_PACKET_TIMES
1166  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_start);
1167 #endif
1168  if (ret != MIXPACKET_SIZE)
1169  {
1170  pFirstMix->m_bRestart = true;
1171  CAMsg::printMsg(LOG_ERR, "CAFirstMix::lm_loopReadFromMix - received returned: %i -- restarting!\n", ret);
1173  break;
1174  }
1175  if (pMixPacket->channel > 0 && pMixPacket->channel < 256)
1176  {
1177 #ifdef DEBUG
1178  CAMsg::printMsg(LOG_DEBUG, "CAFirstMix - sent a packet from the next mix to the ControlChanelDispatcher... \n");
1179 #endif
1180  pControlChannelDispatcher->proccessMixPacket(pMixPacket);
1181  getcurrentTimeMillis(keepaliveLast);
1182  continue;
1183  }
1184  }
1185 #ifdef USE_POOL
1186 #ifdef LOG_PACKET_TIMES
1187  getcurrentTimeMicros(pQueueEntry->pool_timestamp_in);
1188 #endif
1189  pPool->pool((tPoolEntry*)pQueueEntry);
1190 #ifdef LOG_PACKET_TIMES
1191  getcurrentTimeMicros(pQueueEntry->pool_timestamp_out);
1192 #endif
1193 #endif
1194 #ifdef ANON_DEBUG_MODE
1195  if (pMixPacket->flags&CHANNEL_DEBUG)
1196  {
1197  UINT8 base64Payload[DATA_SIZE << 1];
1198  EVP_EncodeBlock(base64Payload, pMixPacket->data, DATA_SIZE);//base64 encoding (without newline!)
1199  CAMsg::printMsg(LOG_DEBUG, "Received Downstream AN.ON packet from previous Mix debug: %s\n", base64Payload);
1200  }
1201 
1202 #endif
1203  pQueue->add(pQueueEntry, sizeof(tQueueEntry));
1204  getcurrentTimeMillis(keepaliveLast);
1205  }
1206  delete pQueueEntry;
1207  pQueueEntry = NULL;
1208  delete pSocketGroup;
1209  pSocketGroup = NULL;
1210  #ifdef USE_POOL
1211  delete pPool;
1212  pPool = NULL;
1213  #endif
1214 
1215  FINISH_STACK("CAFirstMix::fm_loopReadFromMix");
1217  }
#define MONITORING_FIRE_NET_EVENT(e_type)
SINT32 getcurrentTimeMillis(UINT64 &u64Time)
Gets the current Systemtime in milli seconds.
Definition: CAUtil.cpp:252
SINT32 getcurrentTimeMicros(UINT64 &u64Time)
Gets the current Systemtime in micros seconds.
Definition: CAUtil.cpp:280
SINT32 getRandom(UINT32 *val)
Gets 32 random bits.
Definition: CAUtil.cpp:346
UINT32 diff64(const UINT64 &bigop, const UINT64 &smallop)
Definition: CAUtil.hpp:398
void setZero64(UINT64 &op1)
Definition: CAUtil.hpp:355
#define MIX_POOL_TIMEOUT
Definition: StdAfx.h:245
#define MAX_READ_FROM_NEXT_MIX_QUEUE_SIZE
Definition: StdAfx.h:227
#define DUMMY_CHANNEL
Definition: StdAfx.h:246
#define MIX_POOL_SIZE
Definition: StdAfx.h:243
This class "dispatches" messages which it receives via proccessMixPacket() to the associated control ...
bool proccessMixPacket(const MIXPACKET *pPacket)
CAMuxSocket * m_pMuxOut
Definition: CAFirstMix.hpp:490
CAQueue * m_pQueueReadFromMix
Definition: CAFirstMix.hpp:449
CAControlChannelDispatcher * m_pMuxOutControlChannelDispatcher
Definition: CAMix.hpp:195
UINT32 m_u32KeepAliveRecvInterval
Definition: CAMix.hpp:186
SINT32 receive(MIXPACKET *pPacket)
Receives a whole MixPacket.
This class implements the pool strategie of a Mix.
Definition: CAPool.hpp:43
SINT32 pool(tPoolEntry *pPoolEntry)
Definition: CAPool.cpp:83
This is a simple FIFO-Queue.
Definition: CAQueue.hpp:50
SINT32 add(const void *buff, UINT32 size)
Adds data to the Queue.
Definition: CAQueue.cpp:76
UINT32 getSize()
Returns the size of stored data in byte.
Definition: CAQueue.hpp:101
SINT32 add(SOCKET &s)
@ ev_net_nextConnectionClosed
HCHANNEL channel
Definition: typedefs.hpp:117
UINT8 data[DATA_SIZE]
Definition: typedefs.hpp:121
UINT16 flags
Definition: typedefs.hpp:118
Definition: typedefs.hpp:169
MIXPACKET packet
Definition: typedefs.hpp:170
#define MIXPACKET_SIZE
Definition: typedefs.hpp:40
#define CHANNEL_DEBUG
Definition: typedefs.hpp:51
#define CHANNEL_DUMMY
Definition: typedefs.hpp:50
struct t_queue_entry tQueueEntry
Definition: typedefs.hpp:188
#define DATA_SIZE
Definition: typedefs.hpp:69

◆ fm_loopReadFromUsers()

THREAD_RETURN fm_loopReadFromUsers ( void *  )

◆ fm_loopSendToMix()

THREAD_RETURN fm_loopSendToMix ( void *  param)

How to end this thread: 0.

set bRestart=true;

  1. Close connection to next mix
  2. put some bytes (len>MIX_PACKET_SIZE) in the Mix-Output-Queue

Definition at line 363 of file CAFirstMix.cpp.

979  {
980  INIT_STACK;
981  BEGIN_STACK("CAFirstMix::fm_loopSendToMix");
982 
983  CAFirstMix* pFirstMix=(CAFirstMix*)param;
984  CAQueue* pQueue=((CAFirstMix*)param)->m_pQueueSendToMix;
985  CAMuxSocket* pMuxSocket=pFirstMix->m_pMuxOut;
986 
987  UINT32 len;
988  SINT32 ret;
989 
990 /*#ifdef DATA_RETENTION_LOG
991  t_dataretentionLogEntry* pDataRetentionLogEntry=new t_dataretentionLogEntry;
992 #endif
993 */
994 #ifndef USE_POOL
995  tQueueEntry* pQueueEntry=new tQueueEntry;
996  MIXPACKET* pMixPacket=&pQueueEntry->packet;
997  UINT32 u32KeepAliveSendInterval=pFirstMix->m_u32KeepAliveSendInterval;
998  while(!pFirstMix->m_bRestart)
999  {
1000  len=sizeof(tQueueEntry);
1001  ret=pQueue->getOrWait((UINT8*)pQueueEntry,&len,u32KeepAliveSendInterval);
1002  if(ret==E_TIMEDOUT)
1003  {//send a dummy as keep-alvie-traffic
1004  pMixPacket->flags=CHANNEL_DUMMY;
1005  pMixPacket->channel=DUMMY_CHANNEL;
1006  getRandom(pMixPacket->data,DATA_SIZE);
1007  }
1008  else if(ret!=E_SUCCESS||len!=sizeof(tQueueEntry))
1009  {
1010  CAMsg::printMsg(LOG_ERR,"CAFirstMix::lm_loopSendToMix - Error in dequeueing MixPaket\n");
1011  CAMsg::printMsg(LOG_ERR,"ret=%i len=%i\n",ret,len);
1012  break;
1013  }
1014 
1015  if(pMuxSocket->send(pMixPacket)!=MIXPACKET_SIZE)
1016  {
1017  CAMsg::printMsg(LOG_ERR,"CAFirstMix::lm_loopSendToMix - Error in sending MixPaket\n");
1018  break;
1019  }
1020 #if defined (LOG_PACKET_TIMES)
1021  if(!isZero64(pQueueEntry->timestamp_proccessing_start))
1022  {
1023  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end);
1024  pFirstMix->m_pLogPacketStats->addToTimeingStats(*pQueueEntry,pMixPacket->flags,true);
1025  }
1026 #endif
1027 #ifdef DATA_RETENTION_LOG
1028  if((pQueueEntry->packet.flags&CHANNEL_OPEN)!=0)
1029  {
1030  pQueueEntry->dataRetentionLogEntry.t_out=htonl(time(NULL));
1031  pFirstMix->m_pDataRetentionLog->log(&(pQueueEntry->dataRetentionLogEntry));
1032  }
1033 #endif
1034  }
1035  delete pQueueEntry;
1036  pQueueEntry = NULL;
1037 #else
1038  CAPool* pPool=new CAPool(MIX_POOL_SIZE);
1039  tPoolEntry* pPoolEntry=new tPoolEntry;
1040  MIXPACKET* pMixPacket=&pPoolEntry->packet;
1041  while(!pFirstMix->m_bRestart)
1042  {
1043  len=sizeof(tQueueEntry);
1044  ret=pQueue->getOrWait((UINT8*)pPoolEntry,&len,MIX_POOL_TIMEOUT);
1045  if(ret==E_TIMEDOUT)
1046  {
1047  pMixPacket->flags=CHANNEL_DUMMY;
1048  pMixPacket->channel=DUMMY_CHANNEL;
1049  getRandom(pMixPacket->data,DATA_SIZE);
1050  #ifdef LOG_PACKET_TIMES
1051  setZero64(pPoolEntry->timestamp_proccessing_start);
1052  #endif
1053  }
1054  else if(ret!=E_SUCCESS||len!=sizeof(tQueueEntry))
1055  break;
1056  #ifdef LOG_PACKET_TIMES
1057  getcurrentTimeMicros(pPoolEntry->pool_timestamp_in);
1058  #endif
1059  pPool->pool(pPoolEntry);
1060  #ifdef LOG_PACKET_TIMES
1061  getcurrentTimeMicros(pPoolEntry->pool_timestamp_out);
1062  #endif
1063  if(pMuxSocket->send(pMixPacket)!=MIXPACKET_SIZE)
1064  break;
1065  #ifdef LOG_PACKET_TIMES
1066  if(!isZero64(pPoolEntry->timestamp_proccessing_start))
1067  {
1068  getcurrentTimeMicros(pPoolEntry->timestamp_proccessing_end);
1069  pFirstMix->m_pLogPacketStats->addToTimeingStats(*pPoolEntry,pMixPacket->flags,true);
1070  }
1071  #endif
1072  }
1073  delete pPoolEntry;
1074  pPoolEntry = NULL;
1075  delete pPool;
1076  pPool = NULL;
1077 #endif
1078 
1079 /*#ifdef DATA_RETENTION_LOG
1080  delete pDataRetentionLogEntry;
1081 #endif
1082 */
1083  FINISH_STACK("CAFirstMix::fm_loopSendToMix");
1084 
1085  CAMsg::printMsg(LOG_DEBUG,"Exiting Thread SendToMix\n");
1087  }
bool isZero64(UINT64 &op1)
Definition: CAUtil.hpp:464
UINT32 m_u32KeepAliveSendInterval
Definition: CAMix.hpp:187
SINT32 send(MIXPACKET *pPacket)
Sends a MixPacket over the Network.
SINT32 getOrWait(UINT8 *pbuff, UINT32 *psize)
Gets data from the Queue or waits until some data is available, if the Queue is empty.
Definition: CAQueue.cpp:209
UINT16 len
Definition: typedefs.hpp:0
tQueueEntry tPoolEntry
Definition: typedefs.hpp:192
#define CHANNEL_OPEN
Definition: typedefs.hpp:43

◆ iplist_loopDoLogCountries()

THREAD_RETURN iplist_loopDoLogCountries ( void *  param)

Definition at line 541 of file CAFirstMix.cpp.

3068  {
3069  mysql_thread_init();
3070  CAMsg::printMsg(LOG_DEBUG,"Starting iplist_loopDoLogCountries\n");
3071  CAFirstMix* pFirstMix=(CAFirstMix*)param;
3072  UINT32 s=0;
3073  UINT8 buff[255];
3074  memset(buff,0,255);
3076  mysqlEscapeTableName(buff);
3077  while(pFirstMix->m_bRunLogCountries)
3078  {
3080  {
3081  UINT8 aktDate[255];
3082  time_t aktTime=time(NULL);
3083  strftime((char*)aktDate,255,"%Y%m%d%H%M%S",gmtime(&aktTime));
3084  char query[1024];
3085  sprintf(query,"INSERT into `stats_%s` (date,id,count,packets_in,packets_out) VALUES (\"%s\",\"%%u\",\"%%u\",\"%%u\",\"%%u\")",buff,aktDate);
3086  pFirstMix->m_pmutexUser->lock();
3087  for(UINT32 i=0;i<NR_OF_COUNTRIES+1;i++)
3088  {
3089  if(pFirstMix->m_CountryStats[i]>0)
3090  {
3091  char aktQuery[1024];
3092  sprintf(aktQuery,query,i,pFirstMix->m_CountryStats[i],pFirstMix->m_PacketsPerCountryIN[i].getAndzero(),pFirstMix->m_PacketsPerCountryOUT[i].getAndzero());
3093  SINT32 ret=mysql_query(pFirstMix->m_mysqlCon,aktQuery);
3094  if(ret!=0)
3095  {
3096  CAMsg::printMsg(LOG_INFO,"CountryStats DB - failed to update CountryStats DB with new values - error %i\n",ret);
3097  }
3098  }
3099  }
3100  pFirstMix->m_pmutexUser->unlock();
3101  s=0;
3102  }
3103  sSleep(10);
3104  s++;
3105  }
3106  CAMsg::printMsg(LOG_DEBUG,"Exiting iplist_loopDoLogCountries\n");
3107  mysql_thread_end();
3109  }
#define NR_OF_COUNTRIES
void mysqlEscapeTableName(UINT8 *str)
Escape a string so tha it could be used as table anme.
#define LOG_COUNTRIES_INTERVALL
Definition: StdAfx.h:133
SINT32 getCascadeName(UINT8 *name, UINT32 len) const
volatile bool m_bRunLogCountries
Definition: CAFirstMix.hpp:532
tUINT32withLock * m_PacketsPerCountryOUT
Definition: CAFirstMix.hpp:537
CAMutex * m_pmutexUser
Definition: CAFirstMix.hpp:500
MYSQL * m_mysqlCon
Definition: CAFirstMix.hpp:540
tUINT32withLock * m_PacketsPerCountryIN
Definition: CAFirstMix.hpp:536
volatile UINT32 * m_CountryStats
Definition: CAFirstMix.hpp:533
SINT32 unlock()
Definition: CAMutex.hpp:52
SINT32 lock()
Definition: CAMutex.hpp:41

References CAMsg::printMsg().

Here is the call graph for this function: