Examples/TcpReassembly/main.cpp
/**
 * The callback being called by the TCP reassembly module whenever new data arrives on a certain connection
 */
The callback being called by the TCP reassembly module whenever new data arrives on a certain connection
The callback being called by the TCP reassembly module whenever new data arrives on a certain connection
static void tcpReassemblyMsgReadyCallback(int8_t sideIndex, const pcpp::TcpStreamData& tcpData, void* userCookie)
{
	TcpReassemblyConnMgr* connMgr = (TcpReassemblyConnMgr*)userCookie;
	TcpReassemblyConnMgrIter iter = connMgr->find(tcpData.getConnectionData().flowKey);
	if (iter == connMgr->end())
	{
		connMgr->insert(std::make_pair(tcpData.getConnectionData().flowKey, TcpReassemblyData()));
		iter = connMgr->find(tcpData.getConnectionData().flowKey);
	}
	int8_t side;
	if (GlobalConfig::getInstance().separateSides)
		side = sideIndex;
	else
		side = 0;
	if (iter->second.fileStreams[side] == NULL)
	{
		uint32_t flowKeyToCloseFiles;
		int result = GlobalConfig::getInstance().getRecentConnsWithActivity()->put(tcpData.getConnectionData().flowKey, &flowKeyToCloseFiles);
		if (result == 1)
		{
			TcpReassemblyConnMgrIter iter2 = connMgr->find(flowKeyToCloseFiles);
			if (iter2 != connMgr->end())
			{
				for (int index = 0; index < 2; index++)
				{
					if (iter2->second.fileStreams[index] != NULL)
					{
						GlobalConfig::getInstance().closeFileSteam(iter2->second.fileStreams[index]);
						iter2->second.fileStreams[index] = NULL;
						iter2->second.reopenFileStreams[index] = true;
					}
				}
			}
		}
		std::string fileName = GlobalConfig::getInstance().getFileName(tcpData.getConnectionData(), sideIndex, GlobalConfig::getInstance().separateSides) + ".txt";
		iter->second.fileStreams[side] = GlobalConfig::getInstance().openFileStream(fileName, iter->second.reopenFileStreams[side]);
	}
	if (sideIndex != iter->second.curSide)
	{
		iter->second.numOfMessagesFromSide[sideIndex]++;
		iter->second.curSide = sideIndex;
	}
	iter->second.numOfDataPackets[sideIndex]++;
	iter->second.bytesFromSide[sideIndex] += (int)tcpData.getDataLength();
	iter->second.fileStreams[side]->write((char*)tcpData.getData(), tcpData.getDataLength());
}
static void tcpReassemblyMsgReadyCallback ( int8_t sideIndex , const pcpp :: TcpStreamData & tcpData , void * userCookie ) { TcpReassemblyConnMgr * connMgr = ( TcpReassemblyConnMgr * ) userCookie ; TcpReassemblyConnMgrIter iter = connMgr -> find ( tcpData . getConnectionData ( ) . flowKey ) ; if ( iter == connMgr -> end ( ) ) { connMgr -> insert ( std :: make_pair ( tcpData . getConnectionData ( ) . flowKey , TcpReassemblyData ( ) ) ) ; iter = connMgr -> find ( tcpData . getConnectionData ( ) . flowKey ) ; } int8_t side ; if ( GlobalConfig :: getInstance ( ) . separateSides ) side = sideIndex ; else side = 0 ; if ( iter -> second . fileStreams [ side ] == NULL ) { uint32_t flowKeyToCloseFiles ; int result = GlobalConfig :: getInstance ( ) . getRecentConnsWithActivity ( ) -> put ( tcpData . getConnectionData ( ) . flowKey , & flowKeyToCloseFiles ) ; if ( result == 1 ) { TcpReassemblyConnMgrIter iter2 = connMgr -> find ( flowKeyToCloseFiles ) ; if ( iter2 != connMgr -> end ( ) ) { for ( int index = 0 ; index < 2 ; index ++ ) { if ( iter2 -> second . fileStreams [ index ] != NULL ) { GlobalConfig :: getInstance ( ) . closeFileSteam ( iter2 -> second . fileStreams [ index ] ) ; iter2 -> second . fileStreams [ index ] = NULL ; iter2 -> second . reopenFileStreams [ index ] = true ; } } } } std :: string fileName = GlobalConfig :: getInstance ( ) . getFileName ( tcpData . getConnectionData ( ) , sideIndex , GlobalConfig :: getInstance ( ) . separateSides ) + " " ; iter -> second . fileStreams [ side ] = GlobalConfig :: getInstance ( ) . openFileStream ( fileName , iter -> second . reopenFileStreams [ side ] ) ; } if ( sideIndex != iter -> second . curSide ) { iter -> second . numOfMessagesFromSide [ sideIndex ] ++ ; iter -> second . curSide = sideIndex ; } iter -> second . numOfDataPackets [ sideIndex ] ++ ; iter -> second . bytesFromSide [ sideIndex ] += ( int ) tcpData . getDataLength ( ) ; iter -> second . fileStreams [ side ] -> write ( ( char * ) tcpData . getData ( ) , tcpData . getDataLength ( ) ) ; }
The callback being called by the TCP reassembly module whenever new data arrives on a certain connection
The callback being called by the TCP reassembly module whenever new data arrives on a certain connection
// extract the connection manager from the user cookie
 // check if this flow already appears in the connection manager. If not add it
 // if the user wants to write each side in a different file - set side as the sideIndex, otherwise write everything to the same file ("side 0")
 // if the file stream on the relevant side isn't open yet (meaning it's the first data on this connection)
 // add the flow key of this connection to the list of open connections. If the return value isn't NULL it means that there are too many open files
 // and we need to close the connection with least recently used file(s) in order to open a new one.
 // The connection with the least recently used file is the return value
 // if result equals to 1 it means we need to close the open files in this connection (the one with the least recently used files)
 // find the connection from the flow key
 // close files on both sides (if they're open)
 // close the file
 // set the reopen flag to true to indicate that next time this file will be opened it will be opened in append mode (and not overwrite mode)
 // get the file name according to the 5-tuple etc.
 // open the file in overwrite mode (if this is the first time the file is opened) or in append mode (if it was already opened before)
 // if this messages comes on a different side than previous message seen on this connection
 // count number of message in each side
 // set side index as the current active side
 // count number of packets and bytes in each side of the connection
 // write the new data to the file
