Mixe for Privacy and Anonymity in the Internet
Protected Member Functions | List of all members
CALastMixA Class Reference

#include <CALastMixA.hpp>

Inheritance diagram for CALastMixA:
Collaboration diagram for CALastMixA:

Protected Member Functions

SINT32 loop ()
 
- Protected Member Functions inherited from CALastMix
SINT32 init ()
 
virtual SINT32 initOnce ()
 
SINT32 clean ()
 
SINT32 initMixCascadeInfo (DOMElement *)
 This will initialize the XML Cascade Info struct XMLFirstMixToInfoService that is sent to the InfoService in CAInfoService::sendCascadeHelo() More...
 
virtual SINT32 processKeyExchange ()
 Processes the startup communication with the preceeding mix. More...
 
SINT32 setTargets ()
 Reads the configured proxies from options. More...
 
- Protected Member Functions inherited from CAMix
SINT32 checkCompatibility (DOMNode *a_parent, const char *a_mixPosition)
 
SINT32 appendCompatibilityInfo (DOMNode *a_parent)
 
SINT32 addMixInfo (DOMNode *a_element, bool a_bForceFirstNode)
 
SINT32 signXML (DOMNode *a_element)
 

Additional Inherited Members

- Public Types inherited from CAMix
enum  tMixType { FIRST_MIX , MIDDLE_MIX , LAST_MIX , JAP }
 
- Public Member Functions inherited from CALastMix
 CALastMix ()
 
virtual ~CALastMix ()
 
SINT32 reconfigure ()
 
tMixType getType () const
 
- Public Member Functions inherited from CAMixWithReplayDB
 CAMixWithReplayDB ()
 
CADatabasegetReplayDB () const
 
- Public Member Functions inherited from CAMix
 CAMix ()
 
virtual ~CAMix ()
 
SINT32 start ()
 
virtual void shutDown ()
 
virtual bool isShutDown ()
 
SINT32 getMixCascadeInfo (XERCES_CPP_NAMESPACE::DOMDocument *&docMixCascadeInfo)
 Returns the Mix-Cascade info which should be send to the InfoService. More...
 
bool acceptsReconfiguration ()
 
CAControlChannelDispatchergetDownstreamControlChannelDispatcher () const
 
CAControlChannelDispatchergetUpstreamControlChannelDispatcher () const
 
UINT32 getLastConnectionTime ()
 
bool isConnected ()
 
- Public Attributes inherited from CAMixWithReplayDB
UINT64 m_u64ReferenceTime
 
- Static Public Attributes inherited from CAMix
static const UINT32 TIMEOUT_MIX_CONNECTION_ESTABLISHEMENT = 60000
 
- Protected Attributes inherited from CALastMix
volatile bool m_bRestart
 
CAMuxSocketm_pMuxIn
 
CAQueuem_pQueueSendToMix
 
CAQueuem_pQueueReadFromMix
 
CACacheLoadBalancingm_pCacheLB
 
CACacheLoadBalancingm_pSocksLB
 
CACacheLoadBalancingm_pVPNLB
 
CAASymCipherm_pRSA
 
CAThreadm_pthreadSendToMix
 
CAThreadm_pthreadReadFromMix
 
CALastMixChannelListm_pChannelList
 
volatile bool m_bRunLog
 
volatile UINT32 m_logUploadedPackets
 
volatile UINT64 m_logUploadedBytes
 
volatile UINT32 m_logDownloadedPackets
 
volatile UINT64 m_logDownloadedBytes
 
- Protected Attributes inherited from CAMixWithReplayDB
CADatabasem_pReplayDB
 
CAReplayCtrlChannelMsgProcm_pReplayMsgProc
 
- Protected Attributes inherited from CAMix
volatile bool m_bLoop
 
bool m_bReconfiguring
 
volatile bool m_bShutDown
 
CAMultiSignaturem_pMultiSignature
 
CAInfoServicem_pInfoService
 
UINT32 m_u32KeepAliveRecvInterval
 
UINT32 m_u32KeepAliveSendInterval
 
bool m_acceptReconfiguration
 
volatile bool m_bConnected
 
volatile UINT32 m_lLastConnectionTime
 
XERCES_CPP_NAMESPACE::DOMDocument * m_docMixCascadeInfo
 
CAControlChannelDispatcherm_pMuxOutControlChannelDispatcher
 
CAControlChannelDispatcherm_pMuxInControlChannelDispatcher
 

Detailed Description

Definition at line 39 of file CALastMixA.hpp.

Member Function Documentation

◆ loop()

SINT32 CALastMixA::loop ( )
protectedvirtual

Do not realy close the connection - just inform the Queue that it is closed, so that the remaining data will be sent to the server

NEW_MIX_TYPE

Implements CALastMix.

Definition at line 60 of file CALastMixA.cpp.

61  {
62 #ifndef NEW_MIX_TYPE
63  //CASocketList oSocketList;
64 #ifdef DELAY_CHANNELS
65  m_pChannelList->setDelayParameters( CALibProxytest::getOptions()->getDelayChannelUnlimitTraffic(),
66  CALibProxytest::getOptions()->getDelayChannelBucketGrow(),
67  CALibProxytest::getOptions()->getDelayChannelBucketGrowIntervall());
68 #endif
69 #ifdef DELAY_CHANNELS_LATENCY
70  m_pChannelList->setDelayLatencyParameters( CALibProxytest::getOptions()->getDelayChannelLatency());
71 #endif
72 #ifdef HAVE_EPOLL
73  CASocketGroupEpoll* psocketgroupCacheRead=new CASocketGroupEpoll(false);
74  CASocketGroupEpoll* psocketgroupCacheWrite=new CASocketGroupEpoll(true);
75 #else
76  CASocketGroup* psocketgroupCacheRead=new CASocketGroup(false);
77  CASocketGroup* psocketgroupCacheWrite=new CASocketGroup(true);
78 #endif
79  tQueueEntry* pQueueEntry=new tQueueEntry;
80  MIXPACKET* pMixPacket=&pQueueEntry->packet;
81  SINT32 ret;
82  SINT32 countRead;
83  lmChannelListEntry* pChannelListEntry;
84  UINT8* rsaBuff=new UINT8[RSA_SIZE];
85  UINT32 rsaOutLen=RSA_SIZE;
86  UINT8* tmpBuff=new UINT8[MIXPACKET_SIZE];
87  UINT8* ciphertextBuff=new UINT8[DATA_SIZE];
88  UINT8* plaintextBuff=new UINT8[DATA_SIZE - GCM_MAC_SIZE];
89 #ifdef WITH_INTEGRITY_CHECK
90  UINT16 payloadLen;
91  SINT32 retval;
92 #endif
93  bool bAktiv;
97  CAThread* pLogThread=new CAThread((UINT8*)"CALastMixA - LogLoop");
98  m_bRunLog = true;
99  pLogThread->setMainLoop(lm_loopLog);
100  pLogThread->start(this);
101 
102  #ifdef LOG_CRIME
103  bool bUserSurveillance = false;
104  tQueueEntry* pQueueEntryCrime= new tQueueEntry;
105  #endif
106 #ifdef ANON_DEBUG_MODE
107  bool bIsDebugPacket = false;
108 #endif
109 
110  #ifdef LOG_CHANNEL
111  CAMsg::printMsg(LOG_DEBUG,"Channel time log format is as follows: Channel-ID,Channel Start [micros], Channel End [micros], Upload (bytes), Download (bytes), DataAndOpenPacketsFromUser, DataPacketsToUser\n");
112  #endif
113 
114  while (!m_bRestart)
115  {
116  bAktiv = false;
117  //Step 1a reading from previous Mix --> now in separate thread
118  //Step 1b processing MixPackets from previous mix
119  // processing maximal number of current channels packets
120  if (m_pQueueReadFromMix->getSize() >= sizeof(tQueueEntry))
121  {
122  bAktiv = true;
123  UINT32 channels = m_pChannelList->getSize() + 1;
124  for (UINT32 k = 0; k < channels && m_pQueueReadFromMix->getSize() >= sizeof(tQueueEntry); k++)
125  {
126  ret = sizeof(tQueueEntry);
127  m_pQueueReadFromMix->get((UINT8 *)pQueueEntry, (UINT32 *)&ret);
128 #if defined(LOG_PACKET_TIMES) || defined(LOG_CHANNEL)
129  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_start);
130 #endif
131 #ifdef LOG_PACKET_TIMES
132  set64(pQueueEntry->timestamp_proccessing_start, pQueueEntry->timestamp_proccessing_start_OP);
133 #endif
134  if (pMixPacket->channel > 0 && pMixPacket->channel < 256)
135  {
137  continue;
138  }
139  // one packet received
141 #ifdef ANON_DEBUG_MODE
142  if (pMixPacket->flags & CHANNEL_DEBUG)
143  {
144  UINT8 base64Payload[DATA_SIZE << 1];
145  EVP_EncodeBlock(base64Payload, pMixPacket->data, DATA_SIZE); //base64 encoding (without newline!)
146  pMixPacket->flags &= ~CHANNEL_DEBUG;
147  CAMsg::printMsg(LOG_DEBUG, "AN.ON packet debug: %s\n", base64Payload);
148  bIsDebugPacket = true;
149  }
150  else
151  {
152  bIsDebugPacket = false;
153  }
154 #endif
155  pChannelListEntry = m_pChannelList->get(pMixPacket->channel);
156 
157  //check if this packet was marked by the previous mixes for user surveillance
158 #ifdef LOG_CRIME
159  bUserSurveillance = ((pMixPacket->flags & CHANNEL_SIG_CRIME) != 0);
160  pMixPacket->flags &= ~CHANNEL_SIG_CRIME;
161 #endif
162 
163  if (pChannelListEntry == NULL)
164  {
165  if (pMixPacket->flags == CHANNEL_OPEN)
166  {
167 #if defined(ANON_DEBUG_MODE)
168  CAMsg::printMsg(LOG_DEBUG, "New Connection from previous Mix!\n");
169  //keep a copy of whole packet and output it, if something with integrity check went wrong...
170  UINT8 tmpPacketData[DATA_SIZE];
171  memcpy(tmpPacketData, pMixPacket->data, DATA_SIZE);
172 #endif
173 
174 #ifdef _DEBUG
175  CAMsg::printMsg(LOG_DEBUG, "Received a channel open packet for incoming channel: %u\n", pMixPacket->channel);
176 #endif
177 
178  if (m_pRSA->decryptOAEP(pMixPacket->data, rsaBuff, &rsaOutLen) != E_SUCCESS)
179  {
180  CAMsg::printMsg(LOG_ERR, "Error in channel open asym decryption - channel!\n");
181  /* send a close packet signaling the error */
182  getRandom(pMixPacket->data, DATA_SIZE);
183  pMixPacket->flags = CHANNEL_CLOSE;
184 #ifdef LOG_PACKET_TIMES
185  setZero64(pQueueEntry->timestamp_proccessing_start);
186 #endif
187  m_pQueueSendToMix->add(pQueueEntry, sizeof(tQueueEntry));
189  }
190  else // Asym encryption was successfull
191  {
192 #ifdef REPLAY_DETECTION
193  // replace time(NULL) with the real timestamp ()
194  // packet-timestamp + m_u64ReferenceTime
195  UINT32 stamp = ((UINT32)(rsaBuff[13] << 16) + (UINT32)(rsaBuff[14] << 8) + (UINT32)(rsaBuff[15])) * REPLAY_BASE;
196  if (m_pReplayDB->insert(rsaBuff, stamp + m_u64ReferenceTime) != E_SUCCESS)
197  // if(m_pReplayDB->insert(rsaBuff,time(NULL))!=E_SUCCESS)
198  {
199  CAMsg::printMsg(LOG_INFO, "Replay: Duplicate packet ignored.\n");
200  continue;
201  }
202 #endif
203 #ifdef WITH_INTEGRITY_CHECK
204  CASymCipherGCM *newCipher = new CASymCipherGCM();
205  newCipher->setGCMKeys(rsaBuff, rsaBuff + KEY_SIZE);
206 
207  //Decrypt only the first two bytes to get the payload length
208  UINT16 lengthAndFlagsField = 0;
209  newCipher->decryptMessage(rsaBuff + LAST_MIX_SIZE_OF_SYMMETRIC_KEYS, 2, (UINT8 *)&lengthAndFlagsField, false);
210  payloadLen = ntohs(lengthAndFlagsField);
211  payloadLen &= PAYLOAD_LEN_MASK;
213  retval = E_UNKNOWN;
214  else
215  {
216  //prepend the asym decrypted sym encrypted part of the Mix packet to the sym only encrypted part of the mix packet
217  memcpy(pMixPacket->data + RSA_SIZE - rsaOutLen + LAST_MIX_SIZE_OF_SYMMETRIC_KEYS, rsaBuff + LAST_MIX_SIZE_OF_SYMMETRIC_KEYS, rsaOutLen - LAST_MIX_SIZE_OF_SYMMETRIC_KEYS);
218  //now decrpyt the whole sym encrypted part
219  retval = newCipher->decryptMessage(pMixPacket->data + RSA_SIZE - rsaOutLen + LAST_MIX_SIZE_OF_SYMMETRIC_KEYS, payloadLen + GCM_MAC_SIZE + PAYLOAD_HEADER_SIZE, pMixPacket->data, true);
220  }
221 #else
222  CASymChannelCipher *newCipher = CASymChannelCipherFactory::createCipher(CALibProxytest::getOptions()->getSymChannelCipherAlgorithm());
223  newCipher->setKeys(rsaBuff, LAST_MIX_SIZE_OF_SYMMETRIC_KEYS);
224  newCipher->crypt1(
225  pMixPacket->data + RSA_SIZE,
226  pMixPacket->data + rsaOutLen - LAST_MIX_SIZE_OF_SYMMETRIC_KEYS,
227  DATA_SIZE - RSA_SIZE);
228  memcpy(pMixPacket->data, rsaBuff + LAST_MIX_SIZE_OF_SYMMETRIC_KEYS,
229  rsaOutLen - LAST_MIX_SIZE_OF_SYMMETRIC_KEYS);
230 #endif
231 
232 #ifdef LOG_PACKET_TIMES
233  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end_OP);
234 #endif
235 #ifdef WITH_INTEGRITY_CHECK
236  if (retval != E_SUCCESS)
237  {
238  /* invalid MAC -> send channel close packet with integrity error flag */
239  getRandom(pMixPacket->data, DATA_SIZE);
240  pMixPacket->flags = CHANNEL_CLOSE;
241  pMixPacket->payload.len = htons(INTEGRITY_ERROR_FLAG);
242  pMixPacket->payload.type = 0;
243  newCipher->encryptMessage(pMixPacket->data, 3, ciphertextBuff);
244  memcpy(pMixPacket->data, ciphertextBuff, 3 + GCM_MAC_SIZE);
245  delete newCipher;
246  newCipher = NULL;
247 #ifdef LOG_PACKET_TIMES
248  setZero64(pQueueEntry->timestamp_proccessing_start);
249 #endif
250  m_pQueueSendToMix->add(pQueueEntry, sizeof(tQueueEntry));
252 #if defined(ANON_DEBUG_MODE)
253  UINT8 tmpPacketBase64[DATA_SIZE << 1];
254  EVP_EncodeBlock(tmpPacketBase64, tmpPacketData, DATA_SIZE);
255  CAMsg::printMsg(LOG_ERR, "Integrity check failed in channel-open packet: %s\n", tmpPacketBase64);
256 #else
257  CAMsg::printMsg(LOG_ERR, "Integrity check failed in channel-open packet!\n");
258 #endif
259  }
260  else
261  {
262 #if defined(ANON_DEBUG_MODE)
263  UINT8 tmpPacketBase64[DATA_SIZE << 1];
264  EVP_EncodeBlock(tmpPacketBase64, tmpPacketData, DATA_SIZE);
265  CAMsg::printMsg(LOG_ERR, "Integrity check ok in channel-open packet: %s\n", tmpPacketBase64);
266 #endif
267 #endif
268 
269  CASocket *tmpSocket = new CASocket;
271  ret = E_UNKNOWN;
272  if (pMixPacket->payload.type == MIX_PAYLOAD_SOCKS)
273  ptmpLB = m_pSocksLB;
274  else if (pMixPacket->payload.type == MIX_PAYLOAD_VPN)
275  ptmpLB = m_pVPNLB;
276  for (UINT32 count = 0; count < ptmpLB->getElementCount(); count++)
277  {
278  tmpSocket->create();
279  tmpSocket->setRecvBuff(50000);
280  tmpSocket->setSendBuff(5000);
281  ret = tmpSocket->connect(*ptmpLB->get(), LAST_MIX_TO_PROXY_CONNECT_TIMEOUT);
282  if (ret == E_SUCCESS)
283  break;
284  tmpSocket->close();
285  }
286  if (ret != E_SUCCESS)
287  {
288 #if defined(_DEBUG) || defined(DELAY_CHANNELS_LATENCY)
289  CAMsg::printMsg(LOG_DEBUG, "Cannot connect to Squid!\n");
290 #endif
291  delete tmpSocket;
292  tmpSocket = NULL;
293  /* send a close packet signaling the connect error */
294  getRandom(pMixPacket->data, DATA_SIZE);
295  pMixPacket->flags = CHANNEL_CLOSE;
296  pMixPacket->payload.len = 0;
297  pMixPacket->payload.type = CONNECTION_ERROR_FLAG;
298 #ifdef WITH_INTEGRITY_CHECK
299  newCipher->encryptMessage(pMixPacket->data, 3, ciphertextBuff);
300  memcpy(pMixPacket->data, ciphertextBuff, 3 + GCM_MAC_SIZE);
301 #else
302  newCipher->crypt2(pMixPacket->data, pMixPacket->data, DATA_SIZE);
303 #endif
304 #ifdef LOG_PACKET_TIMES
305  setZero64(pQueueEntry->timestamp_proccessing_start);
306 #endif
307  m_pQueueSendToMix->add(pQueueEntry, sizeof(tQueueEntry));
309  delete newCipher;
310  newCipher = NULL;
311  }
312  else
313  { //connection to proxy successful
314  UINT16 payLen = ntohs(pMixPacket->payload.len);
315 
316  //output payload if packet is marked for user surveillance
317 #ifdef LOG_CRIME
318  time_t timeChannelOpened = time(NULL);
319  bool bIsCrime = false;
320  if (bUserSurveillance)
321  {
322  bIsCrime = true;
323  if (CALibProxytest::getOptions()->isPayloadLogged())
324  {
325  UINT8 base64Payload[PAYLOAD_SIZE << 1];
326  EVP_EncodeBlock(base64Payload, pMixPacket->payload.data, payLen); //base64 encoding (without newline!)
327  CAMsg::printMsg(LOG_CRIT, "Crime detection: User surveillance, previous mix channel (opened at: %u): %u - Upstream Payload (Base64 encoded): %s\n", timeChannelOpened, pMixPacket->channel, base64Payload);
328  }
329  /*UINT8 *domain = parseDomainFromPayload(pMixPacket->payload.data, payLen);
330 
331  if(domain != NULL || (CALibProxytest::getOptions()->isPayloadLogged()) )
332  {
333  CAMsg::printMsg(LOG_CRIT,"Crime detection: User surveillance, previous mix channel: %u\n", pMixPacket->channel);
334  if(domain != NULL)
335  {
336  CAMsg::printMsg(LOG_CRIT, "Domain: %s\n", domain);
337  delete [] domain;
338  }
339  if(CALibProxytest::getOptions()->isPayloadLogged())
340  {
342  UINT8 tempPayload[PAYLOAD_SIZE+1];
343  memcpy(tempPayload, pMixPacket->payload.data,payLen);
344  tempPayload[payLen]=0;
345  CAMsg::printMsg(LOG_CRIT, "Payload: %s\n",tempPayload);
346  }
347  }*/
348  }
349 #endif
350 
351 #ifdef _DEBUG
352  UINT8 c = pMixPacket->payload.data[30];
353  pMixPacket->payload.data[30] = 0;
354  CAMsg::printMsg(LOG_DEBUG, "Try sending data to Squid: %s\n", pMixPacket->payload.data);
355  pMixPacket->payload.data[30] = c;
356 #endif
357 #ifdef LOG_CRIME
358  if (payLen <= PAYLOAD_SIZE && checkCrime(pMixPacket->payload.data, payLen, true))
359  {
360  bIsCrime = true;
361  UINT8 crimeBuff[PAYLOAD_SIZE + 1];
362  memset(pQueueEntryCrime, 0, sizeof(tQueueEntry));
363  memset(crimeBuff, 0, PAYLOAD_SIZE + 1);
364  memcpy(crimeBuff, pMixPacket->payload.data, payLen);
365  m_pMuxIn->sigCrime(pMixPacket->channel, &(pQueueEntryCrime->packet));
366  m_pQueueSendToMix->add(pQueueEntryCrime, sizeof(tQueueEntry));
367  int log = LOG_ENCRYPTED;
368  UINT32 srcPort = tmpSocket->getLocalPort();
369  if (!CALibProxytest::getOptions()->isEncryptedLogEnabled())
370  log = LOG_CRIT;
371  CAMsg::printMsg(log, "Crime detected -- previous mix channel: "
372  "%u -- Proxy Connection source port: %u -- Content: \n%s\n",
373  pMixPacket->channel, srcPort,
374  (CALibProxytest::getOptions()->isPayloadLogged() ? crimeBuff : (UINT8 *)"<not logged>"));
375  }
376 #endif
377  if (payLen > PAYLOAD_SIZE || tmpSocket->sendTimeOut(pMixPacket->payload.data, payLen, LAST_MIX_TO_PROXY_SEND_TIMEOUT) == SOCKET_ERROR)
378  {
379 #ifdef _DEBUG
380  CAMsg::printMsg(LOG_DEBUG, "Error sending Data to Squid!\n");
381 #endif
382  tmpSocket->close();
383  delete tmpSocket;
384  tmpSocket = NULL;
385  /* send a close packet signaling the connect error */
386  getRandom(pMixPacket->data, DATA_SIZE);
387  pMixPacket->flags = CHANNEL_CLOSE;
388  pMixPacket->payload.len = 0;
389  pMixPacket->payload.type = CONNECTION_ERROR_FLAG;
390 #ifdef WITH_INTEGRITY_CHECK
391  newCipher->encryptMessage(pMixPacket->data, 3, ciphertextBuff);
392  memcpy(pMixPacket->data, ciphertextBuff, 3 + GCM_MAC_SIZE);
393 #else
394  newCipher->crypt2(pMixPacket->data, pMixPacket->data, DATA_SIZE);
395 #endif
396 #ifdef LOG_PACKET_TIMES
397  setZero64(pQueueEntry->timestamp_proccessing_start);
398 #endif
399  m_pQueueSendToMix->add(pQueueEntry, sizeof(tQueueEntry));
401  delete newCipher;
402  newCipher = NULL;
403 #ifdef LOG_CRIME
404  if (bIsCrime)
405  {
406  int log = LOG_ENCRYPTED;
407  if (!CALibProxytest::getOptions()->isEncryptedLogEnabled())
408  log = LOG_CRIT;
409  CAMsg::printMsg(log, "Crime channel closed -- previous mix channel: %u\n", pMixPacket->channel);
410  }
411 #endif
412  }
413  else
414  {
415  tmpSocket->setNonBlocking(true);
416 #if defined(DELAY_CHANNELS_LATENCY)
417  UINT64 u64temp;
418  getcurrentTimeMillis(u64temp);
419 #endif
420  CAQueue *pQueue = new CAQueue(PAYLOAD_SIZE);
421 #ifdef LASTMIX_CHECK_MEMORY
422  pQueue->logIfSizeGreaterThen(100000);
423 #endif
424  m_pChannelList->add(pMixPacket->channel, tmpSocket, newCipher, pQueue
425 #if defined(LOG_CHANNEL)
426  ,
427  pQueueEntry->timestamp_proccessing_start, payLen
428 #endif
429 #if defined(DELAY_CHANNELS_LATENCY)
430  ,
431  u64temp
432 #endif
433 #ifdef LOG_CRIME
434  ,
435  bIsCrime, (bUserSurveillance && CALibProxytest::getOptions()->isPayloadLogged()), timeChannelOpened
436 #endif
437 #ifdef ANON_DEBUG_MODE
438  ,
439  bIsDebugPacket
440 #endif
441  );
442 #ifdef HAVE_EPOLL
443  psocketgroupCacheRead->add(*tmpSocket, m_pChannelList->get(pMixPacket->channel));
444 #else
445  psocketgroupCacheRead->add(*tmpSocket);
446 #endif
447 #ifdef LOG_PACKET_TIMES
448  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end);
449  m_pLogPacketStats->addToTimeingStats(*pQueueEntry, CHANNEL_OPEN, true);
450 #endif
451 #ifdef DATA_RETENTION_LOG
452  pQueueEntry->dataRetentionLogEntry.t_out = htonl(time(NULL));
453  pQueueEntry->dataRetentionLogEntry.entity.last.channelid = htonl(pMixPacket->channel);
454  pQueueEntry->dataRetentionLogEntry.entity.last.port_out = tmpSocket->getLocalPort();
455  pQueueEntry->dataRetentionLogEntry.entity.last.port_out = htons(pQueueEntry->dataRetentionLogEntry.entity.last.port_out);
456  tmpSocket->getLocalIP(pQueueEntry->dataRetentionLogEntry.entity.last.ip_out);
457  m_pDataRetentionLog->log(&pQueueEntry->dataRetentionLogEntry);
458 #endif
459  }
460  }
461 #ifdef WITH_INTEGRITY_CHECK
462  }
463 #endif
464  }// Asym decryption was sucessfull
465  }//pMixPacket->flags==CHANNEL_OPEN
466  }
467  else
468  {//channellist entry !=NULL
469  if(pMixPacket->flags==CHANNEL_CLOSE)
470  {
473  /*
474  psocketgroupCacheRead->remove(*(pChannelListEntry->pSocket));
475  psocketgroupCacheWrite->remove(*(pChannelListEntry->pSocket));
476  pChannelListEntry->pSocket->close();
477  delete pChannelListEntry->pSocket;
478  pChannelListEntry->pSocket = NULL;
479  delete pChannelListEntry->pCipher;
480  pChannelListEntry->pCipher = NULL;
481  delete pChannelListEntry->pQueueSend;
482  pChannelListEntry->pQueueSend = NULL;
483  */
484  pChannelListEntry->pQueueSend->close();
485 #ifdef HAVE_EPOLL
486  psocketgroupCacheWrite->add(*(pChannelListEntry->pSocket),pChannelListEntry);
487 #else
488  psocketgroupCacheWrite->add(*(pChannelListEntry->pSocket));
489 #endif
490  #if defined (LOG_PACKET_TIMES) ||defined (LOG_CHANNEL)
491  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end);
492  #endif
493  #if defined (LOG_PACKET_TIMES)
494  set64(pQueueEntry->timestamp_proccessing_end_OP,pQueueEntry->timestamp_proccessing_end);
495  m_pLogPacketStats->addToTimeingStats(*pQueueEntry,CHANNEL_CLOSE,true);
496  #endif
497  #ifdef LOG_CHANNEL
498  pChannelListEntry->packetsDataInFromUser++;
499  MACRO_DO_LOG_CHANNEL_CLOSE_FROM_USER
500  #endif
501  //m_pChannelList->removeChannel(pMixPacket->channel);
502  }
503  else if(pMixPacket->flags==CHANNEL_DATA)
504  {
505 #if defined(ANON_DEBUG_MODE)
506  //keep a copy of whole packet and output it, if something with integrity check went wrong...
507  UINT8 tmpPacket[DATA_SIZE];
508  memcpy(tmpPacket, pMixPacket->data, DATA_SIZE);
509 #endif
510  #ifdef LOG_CHANNEL
511  pChannelListEntry->packetsDataInFromUser++;
512  #endif
513  #ifdef WITH_INTEGRITY_CHECK
514  /* decrypt only the first 2 bytes to get the payload length */
515  UINT16 lengthAndFlagsField=0;
516  pChannelListEntry->pCipher->decryptMessage(pMixPacket->data, 2,(UINT8*) &lengthAndFlagsField, false);
517  payloadLen = ntohs(lengthAndFlagsField);
518  payloadLen &= PAYLOAD_LEN_MASK;
519  if (payloadLen > PAYLOAD_SIZE)
520  retval=E_UNKNOWN;
521  else
522  {
523  retval = pChannelListEntry->pCipher->decryptMessage(pMixPacket->data, payloadLen + 3 + GCM_MAC_SIZE, plaintextBuff, true);
524  }
525  if (retval != E_SUCCESS) {
526 #if defined(ANON_DEBUG_MODE)
527  UINT8 tmpPacketBase64[DATA_SIZE << 1];
528  EVP_EncodeBlock(tmpPacketBase64, tmpPacket, DATA_SIZE);
529  CAMsg::printMsg(LOG_ERR, "Integrity check failed in channel-data packet: %s\n", tmpPacketBase64);
530 #else
531  CAMsg::printMsg(LOG_ERR, "Integrity check failed in channel-data packet!\n");
532 #endif
533  /* invalid MAC -> send channel close packet with integrity error flag */
534  psocketgroupCacheRead->remove(*(pChannelListEntry->pSocket));
535  psocketgroupCacheWrite->remove(*(pChannelListEntry->pSocket));
536  pChannelListEntry->pSocket->close();
537  delete pChannelListEntry->pSocket;
538  pChannelListEntry->pSocket = NULL;
539  delete pChannelListEntry->pQueueSend;
540  pChannelListEntry->pQueueSend = NULL;
541  getRandom(pMixPacket->data, DATA_SIZE);
542  pMixPacket->flags = CHANNEL_CLOSE;
543  pMixPacket->payload.len = htons(INTEGRITY_ERROR_FLAG);
544  pMixPacket->payload.type = 0;
545  pChannelListEntry->pCipher->encryptMessage(pMixPacket->data, 3, ciphertextBuff);
546  memcpy(pMixPacket->data, ciphertextBuff, 3 + GCM_MAC_SIZE);
547  delete pChannelListEntry->pCipher;
548  pChannelListEntry->pCipher = NULL;
549  #ifdef LOG_CHANNEL
550  pChannelListEntry->packetsDataOutToUser++;
551  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end);
552  MACRO_DO_LOG_CHANNEL_CLOSE_FROM_MIX
553  #endif
554  m_pChannelList->removeChannel(pMixPacket->channel);
555  #ifdef LOG_PACKET_TIMES
556  setZero64(pQueueEntry->timestamp_proccessing_start);
557  #endif
558  m_pQueueSendToMix->add(pQueueEntry,sizeof(tQueueEntry));
560  } else {
561  memcpy(pMixPacket->data, plaintextBuff, payloadLen + 3);
562  #else
563  pChannelListEntry->pCipher->crypt1(pMixPacket->data,pMixPacket->data,DATA_SIZE);
564  #endif
565  ret=ntohs(pMixPacket->payload.len);
566  if(ret&NEW_FLOW_CONTROL_FLAG)
567  {
568  //CAMsg::printMsg(LOG_DEBUG,"got send me\n");
570  }
571  ret&=PAYLOAD_LEN_MASK;
572  if(ret>=0&&ret<=PAYLOAD_SIZE)
573  {
574  #ifdef LOG_CHANNEL
575  pChannelListEntry->trafficInFromUser+=ret;
576  #endif
577  #ifdef LOG_PACKET_TIMES
578  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end_OP);
579  #endif
580 
581  //output payload if packet is marked for user surveillance
582  #ifdef LOG_CRIME
583  if(bUserSurveillance)
584  {
585  if(CALibProxytest::getOptions()->isPayloadLogged())
586  {
587  UINT8 base64Payload[PAYLOAD_SIZE<<1];
588  EVP_EncodeBlock(base64Payload,pMixPacket->payload.data,ret);//base64 encoding (without newline!)
589  CAMsg::printMsg(LOG_CRIT,"Crime detection: User surveillance, previous mix channel (opened at: %u): %u - Upstream Payload (Base64 encoded): %s\n", pChannelListEntry->timeChannelOpened,pMixPacket->channel,base64Payload);
590  pChannelListEntry->bLogPayload=true;
591  }
592 /* UINT8 *domain = parseDomainFromPayload(pMixPacket->payload.data, ret);
593 
594  if(domain != NULL || (CALibProxytest::getOptions()->isPayloadLogged()) )
595  {
596  CAMsg::printMsg(LOG_CRIT,"Crime detection: User surveillance, previous mix channel: %u\n", pMixPacket->channel);
597  if(domain != NULL)
598  {
599  CAMsg::printMsg(LOG_CRIT, "Domain: %s\n", domain);
600  delete [] domain;
601  }
602  if(CALibProxytest::getOptions()->isPayloadLogged())
603  {
605  UINT8 tempPayload[PAYLOAD_SIZE+1];
606  memcpy(tempPayload, pMixPacket->payload.data,ret);
607  tempPayload[ret]=0;
608  CAMsg::printMsg(LOG_CRIT, "Payload: %s\n",tempPayload);
609  }
610  }
611  */ }
612  else if(checkCrime(pMixPacket->payload.data, ret,false)) // Note: false --> it make no sense to check for URL/Domain in DataPackets
613  {
614  UINT8 crimeBuff[PAYLOAD_SIZE+1];
615  memset(pQueueEntryCrime,0,sizeof(tQueueEntry));
616  memset(crimeBuff,0,PAYLOAD_SIZE+1);
617  memcpy(crimeBuff,pMixPacket->payload.data, ret);
618  m_pMuxIn->sigCrime(pMixPacket->channel, &(pQueueEntryCrime->packet));
619  m_pQueueSendToMix->add(pQueueEntryCrime,sizeof(tQueueEntry));
620  int log=LOG_ENCRYPTED;
621  if(!CALibProxytest::getOptions()->isEncryptedLogEnabled())
622  log=LOG_CRIT;
623  CAMsg::printMsg(log,"Crime detected -- previous mix channel: "
624  "%u -- Content: \n%s\n", pMixPacket->channel,
625  (CALibProxytest::getOptions()->isPayloadLogged() ? crimeBuff : (UINT8 *)"<not logged>"));
626  }
627 
628  #endif
629 
630  ret=pChannelListEntry->pQueueSend->add(pMixPacket->payload.data,ret);
631  }
632  else
633  ret=SOCKET_ERROR;
634  if(ret==SOCKET_ERROR)
635  {
636  psocketgroupCacheRead->remove(*(pChannelListEntry->pSocket));
637  psocketgroupCacheWrite->remove(*(pChannelListEntry->pSocket));
638  pChannelListEntry->pSocket->close();
639  delete pChannelListEntry->pSocket;
640  pChannelListEntry->pSocket = NULL;
641  delete pChannelListEntry->pQueueSend;
642  pChannelListEntry->pQueueSend = NULL;
643  /* send a close packet signaling the connect error */
644  getRandom(pMixPacket->data, DATA_SIZE);
645  pMixPacket->flags = CHANNEL_CLOSE;
646  pMixPacket->payload.len = 0;
647  pMixPacket->payload.type = 0;
648  #ifdef WITH_INTEGRITY_CHECK
649  pChannelListEntry->pCipher->encryptMessage(pMixPacket->data, 3, ciphertextBuff);
650  memcpy(pMixPacket->data, ciphertextBuff, 3 + GCM_MAC_SIZE);
651  #endif
652  delete pChannelListEntry->pCipher;
653  pChannelListEntry->pCipher = NULL;
654  #ifdef LOG_CHANNEL
655  pChannelListEntry->packetsDataOutToUser++;
656  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end);
657  MACRO_DO_LOG_CHANNEL_CLOSE_FROM_MIX
658  #endif
659  m_pChannelList->removeChannel(pMixPacket->channel);
660  #ifdef LOG_PACKET_TIMES
661  setZero64(pQueueEntry->timestamp_proccessing_start);
662  #endif
663  m_pQueueSendToMix->add(pQueueEntry,sizeof(tQueueEntry));
665  }
666  else
667  {
668  //count this packet as Upstream packet...
669  pChannelListEntry->sendmeCounterUpstream++;
670  if(pChannelListEntry->sendmeCounterUpstream>=FLOW_CONTROL_SENDME_SOFT_LIMIT) //we need to sent the SENDME ack down to the client...
671  {
672  getRandom(pMixPacket->data, DATA_SIZE);
673  pMixPacket->flags = CHANNEL_DATA;
674  pMixPacket->payload.len = htons(NEW_FLOW_CONTROL_FLAG); //signal the SENDME
675  pMixPacket->payload.type = 0;
676  #ifdef WITH_INTEGRITY_CHECK
677  pChannelListEntry->pCipher->encryptMessage(pMixPacket->data, 3, ciphertextBuff);
678  memcpy(pMixPacket->data, ciphertextBuff, 3 + GCM_MAC_SIZE);
679  #else
680  pChannelListEntry->pCipher->crypt2(pMixPacket->data,pMixPacket->data,DATA_SIZE);
681  #endif
682  #ifdef LOG_CHANNEL
683  pChannelListEntry->packetsDataOutToUser++;
684  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end);
685  MACRO_DO_LOG_CHANNEL_CLOSE_FROM_MIX
686  #endif
687  #ifdef LOG_PACKET_TIMES
688  setZero64(pQueueEntry->timestamp_proccessing_start);
689  #endif
690  //CAMsg::printMsg(LOG_DEBUG,"sent send me\n");
691  m_pQueueSendToMix->add(pQueueEntry,sizeof(tQueueEntry));
694  }
695 #ifdef HAVE_EPOLL
696  psocketgroupCacheWrite->add(*(pChannelListEntry->pSocket),pChannelListEntry);
697 #else
698  psocketgroupCacheWrite->add(*(pChannelListEntry->pSocket));
699 #endif
700  #ifdef LOG_PACKET_TIMES
701  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end);
702  m_pLogPacketStats->addToTimeingStats(*pQueueEntry,CHANNEL_DATA,true);
703  #endif
704  }
705 #ifdef WITH_INTEGRITY_CHECK
706  }
707 #endif
708  }
709  }
710  }
711  }
712 //end Step 1
713 
714 //Step 2 Sending to Cache...
715  countRead=psocketgroupCacheWrite->select(0);
716  if(countRead>0)
717  {
718  bAktiv=true;
719 #ifdef HAVE_EPOLL
720  pChannelListEntry=(lmChannelListEntry*)psocketgroupCacheWrite->getFirstSignaledSocketData();
721  while(pChannelListEntry!=NULL)
722  {
723 #else
724  pChannelListEntry=m_pChannelList->getFirstSocket();
725  while(pChannelListEntry!=NULL&&countRead>0)
726  {
727  if(psocketgroupCacheWrite->isSignaled(*(pChannelListEntry->pSocket)))
728  {
729  countRead--;
730 #endif
732  ret=pChannelListEntry->pQueueSend->peek(tmpBuff,(UINT32*)&len);
733  len=pChannelListEntry->pSocket->send(tmpBuff,len);
734 #ifdef _DEBUG
735  CAMsg::printMsg(LOG_DEBUG, "Channel %u: Wrote %i bytes to proxy\n", pChannelListEntry->channelIn, len);
736 #endif
737  if(len>=0)
738  {
740  pChannelListEntry->pQueueSend->remove((UINT32*)&len);
741  if(pChannelListEntry->pQueueSend->isEmpty())
742  {
743  if(pChannelListEntry->pQueueSend->isClosed()) //channel was closed by user // Queue: EMPTY + CLOSED
744  {
745  psocketgroupCacheRead->remove(*(pChannelListEntry->pSocket));
746  psocketgroupCacheWrite->remove(*(pChannelListEntry->pSocket));
747  pChannelListEntry->pSocket->close();
748  delete pChannelListEntry->pSocket;
749  pChannelListEntry->pSocket = NULL;
750  delete pChannelListEntry->pCipher;
751  pChannelListEntry->pCipher = NULL;
752  delete pChannelListEntry->pQueueSend;
753  pChannelListEntry->pQueueSend = NULL;
754  m_pChannelList->removeChannel(pChannelListEntry->channelIn);
755  }
756  else //Queue: EMPTY+!CLOSED
757  {//nothing more to write at the moment...
758  psocketgroupCacheWrite->remove(*(pChannelListEntry->pSocket));
759  }
760  }
761  }
762  else
763  {
764  if(len==SOCKET_ERROR)
765  { //do something if send error
766  psocketgroupCacheRead->remove(*(pChannelListEntry->pSocket));
767  psocketgroupCacheWrite->remove(*(pChannelListEntry->pSocket));
768  pChannelListEntry->pSocket->close();
769  delete pChannelListEntry->pSocket;
770  pChannelListEntry->pSocket = NULL;
771  /* send a close packet signaling the connect error */
772  getRandom(pMixPacket->data, DATA_SIZE);
773  pMixPacket->flags = CHANNEL_CLOSE;
774  pMixPacket->payload.len = 0;
775  pMixPacket->payload.type = 0;
776  #ifdef WITH_INTEGRITY_CHECK
777  pChannelListEntry->pCipher->encryptMessage(pMixPacket->data, 3, ciphertextBuff);
778  memcpy(pMixPacket->data, ciphertextBuff, 3 + GCM_MAC_SIZE);
779  #endif
780  delete pChannelListEntry->pCipher;
781  pChannelListEntry->pCipher = NULL;
782  delete pChannelListEntry->pQueueSend;
783  pChannelListEntry->pQueueSend = NULL;
784  pMixPacket->channel=pChannelListEntry->channelIn;
785  #ifdef LOG_PACKET_TIMES
786  setZero64(pQueueEntry->timestamp_proccessing_start);
787  #endif
788  m_pQueueSendToMix->add(pQueueEntry,sizeof(tQueueEntry));
790  #ifdef LOG_CHANNEL
791  pChannelListEntry->packetsDataOutToUser++;
792  #endif
793  #ifdef LOG_CHANNEL
794  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end);
795  MACRO_DO_LOG_CHANNEL_CLOSE_FROM_MIX
796  #endif
797  m_pChannelList->removeChannel(pChannelListEntry->channelIn);
798  }
799  }
800 #ifdef HAVE_EPOLL
801  pChannelListEntry=(lmChannelListEntry*)psocketgroupCacheWrite->getNextSignaledSocketData();
802 #else
803  }
804  pChannelListEntry=m_pChannelList->getNextSocket();
805 #endif
806  }
807  }
808 //End Step 2
809 
810 //Step 3 Reading from Cache....
811 
812  countRead=psocketgroupCacheRead->select(0);
813 #ifdef DELAY_CHANNELS_LATENCY
814  UINT64 current_time_millis;
815  getcurrentTimeMillis(current_time_millis);
816 #endif
818  {
819 #ifdef HAVE_EPOLL
820  pChannelListEntry=(lmChannelListEntry*)psocketgroupCacheRead->getFirstSignaledSocketData();
821  while(pChannelListEntry!=NULL)
822  {
823 #else
824  pChannelListEntry=m_pChannelList->getFirstSocket();
825  while(pChannelListEntry!=NULL&&countRead>0)
826  {
827  if(psocketgroupCacheRead->isSignaled(*(pChannelListEntry->pSocket)))
828  {
829  countRead--;
830 #endif
831  //UINT32 bucketSize;
833  #ifdef DELAY_CHANNELS
834  && ( pChannelListEntry->delayBucket>0)
835  #endif
836  #ifdef DELAY_CHANNELS_LATENCY
837  &&(isGreater64(current_time_millis,pChannelListEntry->timeLatency))
838  #endif
839  )
840  {
841  #ifndef DELAY_CHANNELS
842  ret=pChannelListEntry->pSocket->receive(pMixPacket->payload.data,PAYLOAD_SIZE);
843  #else
844  UINT32 readLen=
845  min(
846  pChannelListEntry->delayBucket,
847  PAYLOAD_SIZE);
848  ret=pChannelListEntry->pSocket->receive(pMixPacket->payload.data,readLen);
849  #endif
850  #ifdef LOG_PACKET_TIMES
851  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_start);
852  set64(pQueueEntry->timestamp_proccessing_start_OP,pQueueEntry->timestamp_proccessing_start);
853  #endif
854  bAktiv=true;
855  if(ret==SOCKET_ERROR||ret==0)
856  {
857  psocketgroupCacheRead->remove(*(pChannelListEntry->pSocket));
858  psocketgroupCacheWrite->remove(*(pChannelListEntry->pSocket));
859  pChannelListEntry->pSocket->close();
860  delete pChannelListEntry->pSocket;
861  pChannelListEntry->pSocket = NULL;
862  /* send a close packet signaling the connect error */
863  getRandom(pMixPacket->data, DATA_SIZE);
864  pMixPacket->flags = CHANNEL_CLOSE;
865  pMixPacket->payload.len = 0;
866  pMixPacket->payload.type = 0;
867  #ifdef WITH_INTEGRITY_CHECK
868  pChannelListEntry->pCipher->encryptMessage(pMixPacket->data, 3, ciphertextBuff);
869  memcpy(pMixPacket->data, ciphertextBuff, 3 + GCM_MAC_SIZE);
870  #endif
871  delete pChannelListEntry->pCipher;
872  pChannelListEntry->pCipher = NULL;
873  delete pChannelListEntry->pQueueSend;
874  pChannelListEntry->pQueueSend = NULL;
875  pMixPacket->channel=pChannelListEntry->channelIn;
876  #ifdef LOG_PACKET_TIMES
877  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end_OP);
878  #endif
879  m_pQueueSendToMix->add(pQueueEntry,sizeof(tQueueEntry));
881  #ifdef LOG_CHANNEL
882  pChannelListEntry->packetsDataOutToUser++;
883  #endif
884  #ifdef LOG_CHANNEL
885  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end);
886  MACRO_DO_LOG_CHANNEL_CLOSE_FROM_MIX
887  #endif
888  m_pChannelList->removeChannel(pChannelListEntry->channelIn);
889  }
890  else
891  {
893  #if defined(LOG_CHANNEL)
894  pChannelListEntry->trafficOutToUser+=ret;
895  #endif
896  #ifdef DELAY_CHANNELS
897  m_pChannelList->reduceDelayBuckets(pChannelListEntry->delayBucketID, ret);
898  #endif
899  pMixPacket->channel=pChannelListEntry->channelIn;
900  pMixPacket->flags=CHANNEL_DATA;
901  pMixPacket->payload.type=0;
902  pMixPacket->payload.len=htons((UINT16)ret);
903  if (ret < PAYLOAD_SIZE)
904  {
905  getRandom(pMixPacket->payload.data+ret, PAYLOAD_SIZE-ret);
906  }
907  //#endif
908  #ifdef LOG_CRIME
909  if(pChannelListEntry->bLogPayload)
910  {
911  UINT8 base64Payload[PAYLOAD_SIZE<<1];
912  EVP_EncodeBlock(base64Payload,pMixPacket->payload.data,ret);//base64 encoding (without newline!)
913  CAMsg::printMsg(LOG_CRIT,"Crime detection: User surveillance, previous mix channel (opened at: %u): %u - Downstream Payload (Base64 encoded): %s\n", pChannelListEntry->timeChannelOpened,pChannelListEntry->channelIn,base64Payload);
914  }
915  #endif //LOG_CRIME
916  #ifdef WITH_INTEGRITY_CHECK
917  pChannelListEntry->pCipher->encryptMessage(pMixPacket->data, ret + 3, ciphertextBuff);
918  memcpy(pMixPacket->data, ciphertextBuff, ret + 3 + GCM_MAC_SIZE);
919  getRandom(pMixPacket->data + ret + 3 + GCM_MAC_SIZE, DATA_SIZE - ret - 3 - GCM_MAC_SIZE);
920  #else
921  pChannelListEntry->pCipher->crypt2(pMixPacket->data,pMixPacket->data,DATA_SIZE);
922  #endif
923  #ifdef LOG_PACKET_TIMES
924  getcurrentTimeMicros(pQueueEntry->timestamp_proccessing_end_OP);
925  #endif
926 #ifdef ANON_DEBUG_MODE
927  if (pChannelListEntry->bDebug )
928  {
929  pMixPacket->flags |= CHANNEL_DEBUG;
930  UINT8 tmpPacketBase64[DATA_SIZE << 1];
931  EVP_EncodeBlock(tmpPacketBase64, pMixPacket->data, DATA_SIZE);
932  CAMsg::printMsg(LOG_ERR, "Put AN.ON debug packet into send queue: %s\n", tmpPacketBase64);
933  }
934 #endif
935 
936  m_pQueueSendToMix->add(pQueueEntry, sizeof(tQueueEntry));
938  #if defined(LOG_CHANNEL)
939  pChannelListEntry->packetsDataOutToUser++;
940  #endif
941  pChannelListEntry->sendmeCounterDownstream++;
942  }
943  }
944 #ifdef HAVE_EPOLL
945  pChannelListEntry=(lmChannelListEntry*)psocketgroupCacheRead->getNextSignaledSocketData();
946 #else
947  }
948  pChannelListEntry=m_pChannelList->getNextSocket();
949 #endif
950  }
951  }
952 //end Step 3
953 
954 //Step 4 Writing to previous Mix
955 // Now in a separate Thread!
956 //
957 //end step 4
958 #ifndef FAST_PROCESSING
959  if(!bAktiv)
960  msSleep(1);
961 #endif
962  }
963 
964 
965 
966 
967 //ERR:
968  CAMsg::printMsg(LOG_CRIT,"CALastMixA - loop() - Seems that we are restarting now!!\n");
969  m_bRunLog=false;
970  clean();
971 #ifdef LOG_CRIME
972  delete pQueueEntryCrime;
973  pQueueEntryCrime = NULL;
974 #endif
975  delete []tmpBuff;
976  tmpBuff = NULL;
977  delete []rsaBuff;
978  rsaBuff = NULL;
979  delete []ciphertextBuff;
980  ciphertextBuff = NULL;
981  delete []plaintextBuff;
982  plaintextBuff = NULL;
983  delete pQueueEntry;
984  pQueueEntry = NULL;
985  pLogThread->join();
986  delete pLogThread;
987  pLogThread = NULL;
988  delete psocketgroupCacheWrite;
989  psocketgroupCacheWrite = NULL;
990  delete psocketgroupCacheRead;
991  psocketgroupCacheRead = NULL;
992 #endif
993  CAMsg::printMsg(LOG_CRIT, "CALastMixA - loop() - finished!!\n");
994  return E_UNKNOWN;
995  }
#define RSA_SIZE
#define LAST_MIX_SIZE_OF_SYMMETRIC_KEYS
Definition: CALastMixA.cpp:57
#define REPLAY_BASE
#define LOG_ENCRYPTED
Definition: CAMsg.hpp:46
#define KEY_SIZE
Definition: CASymCipher.hpp:31
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
SINT32 msSleep(UINT32 ms)
Sleeps ms milliseconds.
Definition: CAUtil.cpp:406
void setZero64(UINT64 &op1)
Definition: CAUtil.hpp:355
void add64(UINT64 &op1, UINT32 op2)
Definition: CAUtil.hpp:375
bool isGreater64(UINT64 &op1, UINT64 &op2)
Definition: CAUtil.hpp:416
void set64(UINT64 &op1, UINT32 op2)
Definition: CAUtil.hpp:321
#define MAX_MIXIN_SEND_QUEUE_SIZE
Definition: StdAfx.h:228
#define LAST_MIX_TO_PROXY_SEND_TIMEOUT
Definition: StdAfx.h:200
#define LAST_MIX_TO_PROXY_CONNECT_TIMEOUT
Definition: StdAfx.h:198
#define SOCKET_ERROR
Definition: StdAfx.h:464
#define FLOW_CONTROL_SENDME_HARD_LIMIT
Definition: StdAfx.h:222
#define min(a, b)
Definition: StdAfx.h:649
#define FLOW_CONTROL_SENDME_SOFT_LIMIT
Definition: StdAfx.h:223
#define max(a, b)
Definition: StdAfx.h:654
unsigned short UINT16
Definition: basetypedefs.h:133
signed int SINT32
Definition: basetypedefs.h:132
unsigned char UINT8
Definition: basetypedefs.h:135
unsigned int UINT32
Definition: basetypedefs.h:131
SINT32 decryptOAEP(const UINT8 *from, UINT8 *to, UINT32 *len)
Decrypts one OAEP encoded block which is stored in from.
This class stores Addresses off different Cache-Proxies.
CASocketAddrINet * get()
Gets the 'next' Address according to the Load-Balancing algorithm.
bool proccessMixPacket(const MIXPACKET *pPacket)
SINT32 insert(UINT8 key[16], UINT64 timestamp)
Inserts this key in the replay DB.
Definition: CADatabase.cpp:93
lmChannelListEntry * get(HCHANNEL channelIn)
SINT32 add(HCHANNEL id, CASocket *pSocket, CASymChannelCipher *pCipher, CAQueue *pQueue)
lmChannelListEntry * getFirstSocket()
lmChannelListEntry * getNextSocket()
SINT32 removeChannel(HCHANNEL channelIn)
volatile bool m_bRunLog
Definition: CALastMix.hpp:189
volatile UINT32 m_logDownloadedPackets
Definition: CALastMix.hpp:192
CAQueue * m_pQueueSendToMix
Definition: CALastMix.hpp:153
volatile UINT64 m_logDownloadedBytes
Definition: CALastMix.hpp:193
volatile UINT64 m_logUploadedBytes
Definition: CALastMix.hpp:191
CACacheLoadBalancing * m_pVPNLB
Definition: CALastMix.hpp:160
CAASymCipher * m_pRSA
Definition: CALastMix.hpp:161
CALastMixChannelList * m_pChannelList
Definition: CALastMix.hpp:166
CAQueue * m_pQueueReadFromMix
Definition: CALastMix.hpp:154
CACacheLoadBalancing * m_pCacheLB
Definition: CALastMix.hpp:158
friend THREAD_RETURN lm_loopLog(void *)
Definition: CALastMix.cpp:591
volatile UINT32 m_logUploadedPackets
Definition: CALastMix.hpp:190
CAMuxSocket * m_pMuxIn
Definition: CALastMix.hpp:152
volatile bool m_bRestart
Definition: CALastMix.hpp:151
SINT32 clean()
Definition: CALastMix.cpp:1031
CACacheLoadBalancing * m_pSocksLB
Definition: CALastMix.hpp:159
static CACmdLnOptions * getOptions()
CAControlChannelDispatcher * m_pMuxInControlChannelDispatcher
Definition: CAMix.hpp:196
CADatabase * m_pReplayDB
static SINT32 printMsg(UINT32 typ, const char *format,...)
Writes a given message to the log.
Definition: CAMsg.cpp:251
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
SINT32 get(UINT8 *pbuff, UINT32 *psize)
Gets up to psize number of bytes from the Queue.
Definition: CAQueue.cpp:148
SINT32 peek(UINT8 *pbuff, UINT32 *psize)
Peeks data from the Queue.
Definition: CAQueue.cpp:258
SINT32 close()
Closes the Queue (for writing).
Definition: CAQueue.hpp:77
SINT32 remove(UINT32 *psize)
Removes data from the Queue.
Definition: CAQueue.cpp:302
UINT32 getSize()
Returns the size of stored data in byte.
Definition: CAQueue.hpp:101
bool isClosed()
Returns true, if the Queue is closed.
Definition: CAQueue.hpp:134
bool isEmpty()
Returns true, if the Queue is empty.
Definition: CAQueue.hpp:125
UINT32 getSizeLookFree()
Returns the size of stored data in byte.
Definition: CAQueue.hpp:116
SINT32 remove(CASocket &s)
bool isSignaled(CASocket &s)
SINT32 add(CASocket &s)
Adds the socket s to the socket group.
virtual SINT32 receive(UINT8 *buff, UINT32 len)
Will receive some bytes from the socket.
Definition: CASocket.cpp:645
virtual SINT32 send(const UINT8 *buff, UINT32 len)
Sends some data over the network.
Definition: CASocket.cpp:400
virtual SINT32 setRecvBuff(UINT32 r)
Definition: CASocket.cpp:846
virtual SINT32 sendTimeOut(const UINT8 *buff, UINT32 len, UINT32 msTimeOut)
Sends some data over the network.
Definition: CASocket.cpp:442
virtual SINT32 setNonBlocking(bool b)
Definition: CASocket.cpp:947
virtual SINT32 setSendBuff(SINT32 r)
Returns < 0 on error, otherwise the new sendbuffersize (which may be less than r)
Definition: CASocket.cpp:862
virtual SINT32 create()
Definition: CASocket.cpp:73
virtual SINT32 getLocalIP(UINT8 r_Ip[4])
LERNGRUPPE Returns the source address of the socket.
Definition: CASocket.cpp:801
virtual SINT32 close()
Definition: CASocket.cpp:351
virtual SINT32 connect(const CASocketAddr &psa)
Definition: CASocket.hpp:64
virtual SINT32 getLocalPort()
Definition: CASocket.cpp:811
static CASymChannelCipher * createCipher(SYMCHANNELCIPHER_ALGORITHM alg)
virtual SINT32 setKeys(const UINT8 *key, UINT32 keysize)=0
Sets the keys for crypt1() and crypt2() either to the same key (if keysize==KEY_SIZE) or to different...
virtual SINT32 crypt2(const UINT8 *in, UINT8 *out, UINT32 len)=0
virtual SINT32 crypt1(const UINT8 *in, UINT8 *out, UINT32 len)=0
This class could be used for encryption/decryption of data (streams) with AES using 128bit GCM mode.
void setGCMKeys(UINT8 *keyRecv, UINT8 *keySend)
SINT32 decryptMessage(const UINT8 *in, UINT32 inlen, UINT8 *out, bool integrityCheck)
SINT32 start(void *param, bool bDaemon=false, bool bSilent=false)
Starts the execution of the main function of this thread.
Definition: CAThread.cpp:115
SINT32 setMainLoop(THREAD_MAIN_TYP fnc)
Sets the main function which will be executed within this thread.
Definition: CAThread.hpp:148
SINT32 join()
Waits for the main function to finish execution.
Definition: CAThread.cpp:187
const SINT32 E_SUCCESS
Definition: errorcodes.hpp:2
#define E_UNKNOWN
Definition: errorcodes.hpp:3
HCHANNEL channel
Definition: typedefs.hpp:117
struct t_MixPacketPayload payload
Definition: typedefs.hpp:122
UINT8 data[DATA_SIZE]
Definition: typedefs.hpp:121
UINT16 flags
Definition: typedefs.hpp:118
UINT8 data[PAYLOAD_SIZE]
Definition: typedefs.hpp:113
CASymChannelCipher * pCipher
Definition: typedefs.hpp:169
MIXPACKET packet
Definition: typedefs.hpp:170
#define CHANNEL_DATA
Definition: typedefs.hpp:42
#define MIXPACKET_SIZE
Definition: typedefs.hpp:40
#define CHANNEL_DEBUG
Definition: typedefs.hpp:51
#define PAYLOAD_SIZE
Definition: typedefs.hpp:73
#define MIX_PAYLOAD_SOCKS
Definition: typedefs.hpp:36
#define MIX_PAYLOAD_VPN
Definition: typedefs.hpp:37
#define GCM_MAC_SIZE
Definition: typedefs.hpp:78
#define CHANNEL_CLOSE
Definition: typedefs.hpp:47
#define NEW_FLOW_CONTROL_FLAG
Definition: typedefs.hpp:63
struct t_queue_entry tQueueEntry
Definition: typedefs.hpp:188
#define PAYLOAD_LEN_MASK
Definition: typedefs.hpp:79
UINT16 len
Definition: typedefs.hpp:0
#define CHANNEL_SIG_CRIME
Definition: typedefs.hpp:58
#define PAYLOAD_HEADER_SIZE
Definition: typedefs.hpp:76
#define CHANNEL_OPEN
Definition: typedefs.hpp:43
#define DATA_SIZE
Definition: typedefs.hpp:69
#define CONNECTION_ERROR_FLAG
Definition: typedefs.hpp:67
#define INTEGRITY_ERROR_FLAG
Definition: typedefs.hpp:65

References CASocketGroupEpoll::add(), CAQueue::add(), CALastMixChannelList::add(), add64(), CAThreadPool::addRequest(), t_MixPacket::channel, CHANNEL_CLOSE, CHANNEL_DATA, CHANNEL_DEBUG, CHANNEL_OPEN, CHANNEL_SIG_CRIME, t_lastmixchannellist::channelIn, CALastMix::clean(), CAQueue::close(), CASocket::close(), CASocket::connect(), CONNECTION_ERROR_FLAG, CASocket::create(), CASymChannelCipherFactory::createCipher(), CASymChannelCipher::crypt1(), CASymChannelCipher::crypt2(), t_MixPacket::data, t_MixPacketPayload::data, DATA_SIZE, CASymCipherGCM::decryptMessage(), CAASymCipher::decryptOAEP(), CAThreadPool::destroy(), E_SUCCESS, E_UNKNOWN, CASymCipherGCM::encryptMessage(), t_MixPacket::flags, FLOW_CONTROL_SENDME_HARD_LIMIT, FLOW_CONTROL_SENDME_SOFT_LIMIT, GCM_MAC_SIZE, CACacheLoadBalancing::get(), CALastMixChannelList::get(), CAQueue::get(), getcurrentTimeMicros(), getcurrentTimeMillis(), CACacheLoadBalancing::getElementCount(), CASocketGroupEpoll::getFirstSignaledSocketData(), CALastMixChannelList::getFirstSocket(), CASocket::getLocalIP(), CASocket::getLocalPort(), CASocketGroupEpoll::getNextSignaledSocketData(), CALastMixChannelList::getNextSocket(), CALibProxytest::getOptions(), getRandom(), CALastMixChannelList::getSize(), CAQueue::getSize(), CAQueue::getSizeLookFree(), CADatabase::insert(), INTEGRITY_ERROR_FLAG, CAQueue::isClosed(), CAQueue::isEmpty(), isGreater64(), CASocketGroupEpoll::isSignaled(), CAThread::join(), KEY_SIZE, LAST_MIX_SIZE_OF_SYMMETRIC_KEYS, LAST_MIX_TO_PROXY_CONNECT_TIMEOUT, LAST_MIX_TO_PROXY_SEND_TIMEOUT, len, t_MixPacketPayload::len, CALastMix::lm_loopLog, LOG_ENCRYPTED, CALastMix::m_bRestart, CALastMix::m_bRunLog, CALastMix::m_logDownloadedBytes, CALastMix::m_logDownloadedPackets, CALastMix::m_logUploadedBytes, CALastMix::m_logUploadedPackets, CALastMix::m_pCacheLB, CALastMix::m_pChannelList, CALastMix::m_pMuxIn, CAMix::m_pMuxInControlChannelDispatcher, CALastMix::m_pQueueReadFromMix, CALastMix::m_pQueueSendToMix, CAMixWithReplayDB::m_pReplayDB, CALastMix::m_pRSA, CALastMix::m_pSocksLB, CALastMix::m_pVPNLB, CAMixWithReplayDB::m_u64ReferenceTime, max, MAX_MIXIN_SEND_QUEUE_SIZE, min, MIX_PAYLOAD_SOCKS, MIX_PAYLOAD_VPN, MIXPACKET_SIZE, msSleep(), NEW_FLOW_CONTROL_FLAG, t_queue_entry::packet, t_MixPacket::payload, PAYLOAD_HEADER_SIZE, PAYLOAD_LEN_MASK, PAYLOAD_SIZE, t_lastmixchannellist::pCipher, CAQueue::peek(), pMix, t_lastmixchannellist::pQueueSend, CAMsg::printMsg(), CAControlChannelDispatcher::proccessMixPacket(), t_lastmixchannellist::pSocket, CASocket::receive(), CASocketGroupEpoll::remove(), CAQueue::remove(), CALastMixChannelList::removeChannel(), REPLAY_BASE, RSA_SIZE, CASocketGroupEpoll::select(), CASocket::send(), t_lastmixchannellist::sendmeCounterDownstream, t_lastmixchannellist::sendmeCounterUpstream, CASocket::sendTimeOut(), set64(), CASymCipherGCM::setGCMKeys(), CAThread::setMainLoop(), CASocket::setNonBlocking(), CASocket::setRecvBuff(), CASocket::setSendBuff(), setZero64(), SOCKET_ERROR, CAThread::start(), THREAD_RETURN, THREAD_RETURN_SUCCESS, and t_MixPacketPayload::type.


The documentation for this class was generated from the following files: