some more protocol implementations, not yet ready

This commit is contained in:
Volker Fischer 2006-02-20 21:09:36 +00:00
parent 6e692a6d37
commit f7e8634ca9
8 changed files with 167 additions and 70 deletions

View file

@ -157,13 +157,15 @@ void CChannelSet::GetBlockAllConC ( CVector<int>& vecChanID,
} }
void CChannelSet::GetConCliParam ( CVector<CHostAddress>& vecHostAddresses, void CChannelSet::GetConCliParam ( CVector<CHostAddress>& vecHostAddresses,
CVector<double>& vecdSamOffs ) CVector<double>& vecdSamOffs,
CVector<int>& veciJitBufSize )
{ {
CHostAddress InetAddr; CHostAddress InetAddr;
/* init return values */ /* init return values */
vecHostAddresses.Init ( MAX_NUM_CHANNELS ); vecHostAddresses.Init ( MAX_NUM_CHANNELS );
vecdSamOffs.Init ( MAX_NUM_CHANNELS ); vecdSamOffs.Init ( MAX_NUM_CHANNELS );
veciJitBufSize.Init ( MAX_NUM_CHANNELS );
/* Check all possible channels */ /* Check all possible channels */
for ( int i = 0; i < MAX_NUM_CHANNELS; i++ ) for ( int i = 0; i < MAX_NUM_CHANNELS; i++ )
@ -173,6 +175,7 @@ void CChannelSet::GetConCliParam ( CVector<CHostAddress>& vecHostAddresses,
/* add new address and sample rate offset to vectors */ /* add new address and sample rate offset to vectors */
vecHostAddresses[i] = InetAddr; vecHostAddresses[i] = InetAddr;
vecdSamOffs[i] = vecChannels[i].GetResampleOffset (); vecdSamOffs[i] = vecChannels[i].GetResampleOffset ();
veciJitBufSize[i] = vecChannels[i].GetSockBufSize ();
} }
} }
} }
@ -244,19 +247,19 @@ bool CChannel::GetAddress(CHostAddress& RetAddr)
} }
} }
bool CChannel::PutData(const CVector<unsigned char>& vecbyData, bool CChannel::PutData ( const CVector<unsigned char>& vecbyData,
int iNumBytes) int iNumBytes )
{ {
bool bRet = true; bool bRet = true;
Mutex.lock(); /* put mutex lock */ Mutex.lock (); /* put mutex lock */
/* only process if packet has correct size */ /* only process if packet has correct size */
if (iNumBytes == iAudComprSize) if ( iNumBytes == iAudComprSize )
{ {
/* decompress audio */ /* decompress audio */
CVector<short> vecsDecomprAudio(BLOCK_SIZE_SAMPLES); CVector<short> vecsDecomprAudio ( BLOCK_SIZE_SAMPLES );
vecsDecomprAudio = AudioCompression.Decode(vecbyData); vecsDecomprAudio = AudioCompression.Decode ( vecbyData );
/* do resampling to compensate for sample rate offsets in the /* do resampling to compensate for sample rate offsets in the
different sound cards of the clients */ different sound cards of the clients */
@ -273,20 +276,30 @@ for (int i = 0; i < BLOCK_SIZE_SAMPLES; i++)
vecdResOutData[i] = (double) vecsDecomprAudio[i]; vecdResOutData[i] = (double) vecsDecomprAudio[i];
bRet = SockBuf.Put(vecdResOutData); bRet = SockBuf.Put ( vecdResOutData );
/* reset time-out counter */ /* reset time-out counter */
iConTimeOut = CON_TIME_OUT_CNT_MAX; iConTimeOut = CON_TIME_OUT_CNT_MAX;
} }
else if (iNumBytes == 1) else if ( iNumBytes == 1 )
{ {
/* time stamp packet */ /* time stamp packet */
SampleOffsetEst.AddTimeStampIdx(vecbyData[0]); SampleOffsetEst.AddTimeStampIdx ( vecbyData[0] );
} }
else else
bRet = false; /* wrong packet size */ {
Mutex.unlock(); /* put mutex unlock */
// TODO add protocol parsing here
ClientProtocol.ParseMessage ( vecbyData, iNumBytes );
bRet = false; /* wrong packet size */
}
Mutex.unlock (); /* put mutex unlock */
return bRet; return bRet;
} }

View file

@ -32,6 +32,7 @@
#include "audiocompr.h" #include "audiocompr.h"
#include "util.h" #include "util.h"
#include "resample.h" #include "resample.h"
#include "protocol.h"
/* Definitions ****************************************************************/ /* Definitions ****************************************************************/
@ -117,6 +118,11 @@ protected:
/* network output conversion buffer */ /* network output conversion buffer */
CConvBuf ConvBuf; CConvBuf ConvBuf;
// TEST TODO: better implementation, now this object is created in server AND client which is not good
CClientProtocol ClientProtocol;
/* time stamp index counter */ /* time stamp index counter */
Q_UINT8 byTimeStampIdxCnt; Q_UINT8 byTimeStampIdxCnt;
int iTimeStampActCnt; int iTimeStampActCnt;
@ -143,7 +149,8 @@ public:
void GetBlockAllConC(CVector<int>& vecChanID, void GetBlockAllConC(CVector<int>& vecChanID,
CVector<CVector<double> >& vecvecdData); CVector<CVector<double> >& vecvecdData);
void GetConCliParam(CVector<CHostAddress>& vecHostAddresses, void GetConCliParam(CVector<CHostAddress>& vecHostAddresses,
CVector<double>& vecdSamOffs); CVector<double>& vecdSamOffs,
CVector<int>& veciJitBufSize);
/* access functions for actual channels */ /* access functions for actual channels */
bool IsConnected(const int iChanNum) bool IsConnected(const int iChanNum)

View file

@ -54,7 +54,10 @@ CLlconServerDlg::CLlconServerDlg ( CServer* pNServP, QWidget* parent,
ListViewClients->setColumnAlignment(1, Qt::AlignCenter); ListViewClients->setColumnAlignment(1, Qt::AlignCenter);
ListViewClients->addColumn(tr("Get")); ListViewClients->addColumn(tr("Get"));
ListViewClients->setColumnAlignment(2, Qt::AlignCenter); ListViewClients->setColumnAlignment(2, Qt::AlignCenter);
ListViewClients->addColumn(tr("Jitter buffer size"));
ListViewClients->setColumnAlignment(3, Qt::AlignRight);
ListViewClients->addColumn(tr("Sample-rate offset [Hz]")); ListViewClients->addColumn(tr("Sample-rate offset [Hz]"));
ListViewClients->setColumnAlignment(4, Qt::AlignRight);
ListViewClients->clear(); ListViewClients->clear();
/* insert items in reverse order because in Windows all of them are /* insert items in reverse order because in Windows all of them are
@ -106,11 +109,12 @@ void CLlconServerDlg::OnTimer()
{ {
CVector<CHostAddress> vecHostAddresses; CVector<CHostAddress> vecHostAddresses;
CVector<double> vecdSamOffs; CVector<double> vecdSamOffs;
CVector<int> veciJitBufSize;
double dCurTiStdDev; double dCurTiStdDev;
ListViewMutex.lock(); ListViewMutex.lock();
pServer->GetConCliParam(vecHostAddresses, vecdSamOffs); pServer->GetConCliParam(vecHostAddresses, vecdSamOffs, veciJitBufSize);
/* fill list with connected clients */ /* fill list with connected clients */
for (int i = 0; i < MAX_NUM_CHANNELS; i++) for (int i = 0; i < MAX_NUM_CHANNELS; i++)
@ -122,9 +126,13 @@ void CLlconServerDlg::OnTimer()
vecHostAddresses[i].InetAddr.toString().latin1(), vecHostAddresses[i].InetAddr.toString().latin1(),
vecHostAddresses[i].iPort) /* IP, port */); vecHostAddresses[i].iPort) /* IP, port */);
/* jitter buffer size */
vecpListViewItems[i]->setText(3,
QString().setNum(veciJitBufSize[i]));
/* sample rate offset */ /* sample rate offset */
// FIXME disable sample rate estimation result label since estimation does not work // FIXME disable sample rate estimation result label since estimation does not work
// vecpListViewItems[i]->setText(3, // vecpListViewItems[i]->setText(4,
// QString().sprintf("%5.2f", vecdSamOffs[i])); // QString().sprintf("%5.2f", vecdSamOffs[i]));
#ifndef _WIN32 #ifndef _WIN32

View file

@ -7,9 +7,13 @@
Protocol message definition Protocol message definition
+-----------+------------+-----------------+--------------+-------------+
| 2 byte ID | 1 byte cnt | 2 byte length n | n bytes data | 2 bytes CRC | MAIN FRAME
+-----------+------------+-----------------+--------------+-------------+ ----------
+------------+------------+------------------+--------------+-------------+
| 2 bytes ID | 1 byte cnt | 2 bytes length n | n bytes data | 2 bytes CRC |
+------------+------------+------------------+--------------+-------------+
- message ID defined by the defines PROTMESSID_x - message ID defined by the defines PROTMESSID_x
- cnt: counter which is increment for each message and wraps around at 255 - cnt: counter which is increment for each message and wraps around at 255
@ -18,6 +22,19 @@ Protocol message definition
- 16 bits CRC, calculating over the entire message, is transmitted inverted - 16 bits CRC, calculating over the entire message, is transmitted inverted
Generator polynom: G_16(x) = x^16 + x^12 + x^5 + 1, initial state: all ones Generator polynom: G_16(x) = x^16 + x^12 + x^5 + 1, initial state: all ones
MESSAGES
--------
- Jitter buffer size: PROTMESSID_JITT_BUF_SIZE
+--------------------------+
| 2 bytes number of blocks |
+--------------------------+
* *
****************************************************************************** ******************************************************************************
* *
@ -42,25 +59,62 @@ Protocol message definition
/* Implementation *************************************************************/ /* Implementation *************************************************************/
bool CClientProtocol::ParseMessage ( const CVector<unsigned char>& vecbyData,
const int iNumBytes )
{
/*
return code: true -> ok; false -> error
*/
int iRecCounter, iRecID;
CVector<uint8_t> vecData;
// convert unsigned char in uint8_t, TODO convert all buffers in uint8_t
CVector<uint8_t> vecbyDataConv ( vecbyData.Size () );
for ( int i = 0; i < vecbyData.Size (); i++ ) {
vecbyDataConv[i] = static_cast<uint8_t> ( vecbyData[i] );
}
if ( ParseMessageFrame ( vecbyDataConv, iRecCounter, iRecID, vecData ) )
{
switch ( iRecID )
{
case PROTMESSID_ACKN:
// TODO implement acknowledge code -> do implementation in CProtocol since
// it can be used in the server protocol, too
break;
}
return true; // everything was ok
}
else
{
return false; // return error code
}
}
void CClientProtocol::CreateJitBufMes ( const int iJitBufSize )
{
CVector<uint8_t> vecData ( 2 );
unsigned int iPos = 0;
// build data vector
PutValOnStream ( vecData, iPos, static_cast<uint32_t> ( iJitBufSize ), 2 );
// build complete message
GenMessageFrame ( vecMessage, iCounter, PROTMESSID_JITT_BUF_SIZE, vecData );
}
/******************************************************************************\ /******************************************************************************\
* Message generation (parsing) * * Message generation (parsing) *
\******************************************************************************/ \******************************************************************************/
bool CProtocol::ParseMessage ( const CVector<uint8_t>& vecIn, bool CProtocol::ParseMessageFrame ( const CVector<uint8_t>& vecIn,
int& iCnt, int& iCnt,
int& iID, int& iID,
CVector<uint8_t>& vecData ) CVector<uint8_t>& vecData )
{ {
/* /*
return code: true -> ok; false -> error return code: true -> ok; false -> error
@ -143,10 +197,10 @@ uint32_t CProtocol::GetValFromStream ( const CVector<uint8_t>& vecIn,
return iRet; return iRet;
} }
void CProtocol::GenMessage ( CVector<uint8_t>& vecOut, void CProtocol::GenMessageFrame ( CVector<uint8_t>& vecOut,
const int iCnt, const int iCnt,
const int iID, const int iID,
const CVector<uint8_t>& vecData ) const CVector<uint8_t>& vecData )
{ {
int i; int i;

View file

@ -45,19 +45,19 @@
class CProtocol class CProtocol
{ {
public: public:
CProtocol() : iCounter(0) {} CProtocol () : iCounter ( 0 ) {}
virtual ~CProtocol() {} virtual ~CProtocol () {}
protected: protected:
bool ParseMessage ( const CVector<uint8_t>& vecIn, bool ParseMessageFrame ( const CVector<uint8_t>& vecIn,
int& iCnt, int& iCnt,
int& iID, int& iID,
CVector<uint8_t>& vecData ); CVector<uint8_t>& vecData );
void GenMessage ( CVector<uint8_t>& vecOut, void GenMessageFrame ( CVector<uint8_t>& vecOut,
const int iCnt, const int iCnt,
const int iID, const int iID,
const CVector<uint8_t>& vecData); const CVector<uint8_t>& vecData);
void PutValOnStream ( CVector<uint8_t>& vecIn, void PutValOnStream ( CVector<uint8_t>& vecIn,
unsigned int& iPos, unsigned int& iPos,
@ -68,38 +68,44 @@ protected:
unsigned int& iPos, unsigned int& iPos,
const unsigned int iNumOfBytes ); const unsigned int iNumOfBytes );
uint8_t iCounter; CVector<uint8_t> vecMessage;
uint8_t iCounter;
}; };
class CServerProtocol : public CProtocol
{
public:
CServerProtocol() {}
virtual ~CServerProtocol() {}
protected:
};
class CClientProtocol : public CProtocol class CClientProtocol : public CProtocol
{ {
public: public:
CClientProtocol() {} CClientProtocol () {}
virtual ~CClientProtocol() {} virtual ~CClientProtocol () {}
void CreateJitBufMes ( const int iJitBufSize );
bool ParseMessage ( const CVector<unsigned char>& vecbyData,
const int iNumBytes );
protected: protected:
}; };
class CProtMessage
class CServerProtocol : public CProtocol
{ {
public: public:
CProtMessage () {} CServerProtocol () {}
virtual ~CProtMessage () {} virtual ~CServerProtocol () {}
bool ParseMessage ( const CVector<unsigned char>& vecbyData,
const int iNumBytes );
protected: protected:
}; };
#endif /* !defined(PROTOCOL_H__3B123453_4344_BB2392354455IUHF1912__INCLUDED_) */ #endif /* !defined(PROTOCOL_H__3B123453_4344_BB2392354455IUHF1912__INCLUDED_) */

View file

@ -36,6 +36,12 @@ CServer::CServer () : Socket ( &ChannelSet, this )
/* connect timer timeout signal */ /* connect timer timeout signal */
QObject::connect ( &Timer, SIGNAL ( timeout () ), QObject::connect ( &Timer, SIGNAL ( timeout () ),
this, SLOT ( OnTimer () ) ); this, SLOT ( OnTimer () ) );
#ifdef _WIN32
// event handling of custom events seems not to work under Windows in this
// class, do not use automatic start/stop of server in Windows version
Start ();
#endif
} }
void CServer::Start () void CServer::Start ()
@ -104,7 +110,11 @@ void CServer::OnTimer ()
{ {
// Disable server if no clients are connected. In this case the server // Disable server if no clients are connected. In this case the server
// does not consume any significant CPU when no client is connected. // does not consume any significant CPU when no client is connected.
#ifndef _WIN32
// event handling of custom events seems not to work under Windows in this
// class, do not use automatic start/stop of server in Windows version
Stop (); Stop ();
#endif
} }
} }

View file

@ -49,8 +49,11 @@ public:
void Stop (); void Stop ();
bool IsRunning() { return Timer.isActive (); } bool IsRunning() { return Timer.isActive (); }
void GetConCliParam ( CVector<CHostAddress>& vecHostAddresses, void GetConCliParam ( CVector<CHostAddress>& vecHostAddresses,
CVector<double>& vecdSamOffs ) CVector<double>& vecdSamOffs, CVector<int>& veciJitBufSize )
{ ChannelSet.GetConCliParam ( vecHostAddresses, vecdSamOffs ); } {
ChannelSet.GetConCliParam ( vecHostAddresses, vecdSamOffs,
veciJitBufSize );
}
bool GetTimingStdDev ( double& dCurTiStdDev ); bool GetTimingStdDev ( double& dCurTiStdDev );

View file

@ -127,13 +127,9 @@ void CSocket::OnDataReceived ()
{ {
/* server */ /* server */
// a packet was received, tell the server object to wake up if it // a packet was received, tell the server object to wake up if it
// is in sleep mode // is in sleep mode (Qt will delete the event object when done)
CLlconEvent* LlconEv = QThread::postEvent ( pServer,
new CLlconEvent ( MS_PACKET_RECEIVED, 0, 0 ); new CLlconEvent ( MS_PACKET_RECEIVED, 0, 0 ) );
/* Qt will delete the event object when done */
QThread::postEvent ( pServer, LlconEv );
pChannelSet->PutData ( vecbyRecBuf, iNumBytesRead, RecHostAddr ); pChannelSet->PutData ( vecbyRecBuf, iNumBytesRead, RecHostAddr );
} }