Commit fb2205a8 authored by Alexandre Savard's avatar Alexandre Savard
Browse files

[#1883] Fix mem leaks in audio rtp

parent 4ba8ad9b
......@@ -43,23 +43,26 @@
////////////////////////////////////////////////////////////////////////////////
// AudioRtp
////////////////////////////////////////////////////////////////////////////////
AudioRtp::AudioRtp() :_RTXThread (0), _symmetric(), _threadMutex()
AudioRtp::AudioRtp() :_RTXThread (0), _symmetric(), _rtpMutex()
{
}
AudioRtp::~AudioRtp (void)
{
ost::MutexLock m (_threadMutex);
ost::MutexLock m (_rtpMutex);
delete _RTXThread;
_RTXThread = 0;
if (_RTXThread != _RTXThread)
{
delete _RTXThread;
_RTXThread = 0;
}
}
void
AudioRtp::createNewSession (SIPCall *ca)
{
ost::MutexLock m (_threadMutex);
ost::MutexLock m (_rtpMutex);
_debug ("AudioRtp::Create new rtp session\n");
......@@ -83,7 +86,7 @@ AudioRtp::createNewSession (SIPCall *ca)
int
AudioRtp::start (void)
{
ost::MutexLock m (_threadMutex);
ost::MutexLock m (_rtpMutex);
if (_RTXThread == 0) {
_debug ("! ARTP Failure: Cannot start audiortp thread since not yet created\n");
......@@ -109,7 +112,7 @@ bool
AudioRtp::closeRtpSession ()
{
ost::MutexLock m (_threadMutex);
ost::MutexLock m (_rtpMutex);
// This will make RTP threads finish.
_debug ("AudioRtp::Stopping rtp session\n");
......@@ -174,9 +177,9 @@ AudioRtpRTX::AudioRtpRTX (SIPCall *sipcall, bool sym) : time (new ost::Time()),
AudioRtpRTX::~AudioRtpRTX ()
{
// ost::MutexLock m (_threadMutex);
ost::MutexLock m (_rtpRtxMutex);
_debug ("Delete AudioRtpRTX instance\n");
_debug ("Delete AudioRtpRTX instance in callid %s\n", _ca->getCallId().c_str());
try {
this->terminate();
......@@ -188,8 +191,7 @@ AudioRtpRTX::~AudioRtpRTX ()
_debug("Unbind call id %s from all participants\n", _ca->getCallId().c_str());
_audiolayer->getMainBuffer()->unBindAll(_ca->getCallId());
_ca = 0;
_debug("DELETE print micData address %p\n", micData);
delete [] micData;
micData = NULL;
delete [] micDataConverted;
......@@ -208,6 +210,7 @@ AudioRtpRTX::~AudioRtpRTX ()
delete converter;
converter = NULL;
_ca = 0;
// _session->terminate();
delete _session;
......@@ -221,17 +224,24 @@ AudioRtpRTX::~AudioRtpRTX ()
void
AudioRtpRTX::initBuffers()
{
ost::MutexLock m (_rtpRtxMutex);
_debug("AudioRtpRTX::initBuffers Init RTP buffers for %s\n", _ca->getCallId().c_str());
converter = new SamplerateConverter (_layerSampleRate , _layerFrameSize);
int nbSamplesMax = (int) (_layerSampleRate * _layerFrameSize /1000);
_debug("AudioRtpRTX::initBuffers NBSAMPLEMAX %i\n", nbSamplesMax);
micData = new SFLDataFormat[nbSamplesMax];
_debug("CREATE print micData address %p\n", micData);
micDataConverted = new SFLDataFormat[nbSamplesMax];
micDataEncoded = new unsigned char[nbSamplesMax];
spkrDataConverted = new SFLDataFormat[nbSamplesMax];
spkrDataDecoded = new SFLDataFormat[nbSamplesMax];
Manager::instance().addStream(_ca->getCallId());
// _audiolayer->getMainBuffer()->bindCallID(_ca->getCallId());
}
......@@ -356,10 +366,10 @@ AudioRtpRTX::processDataEncode()
// available bytes inside ringbuffer
int availBytesFromMic = _audiolayer->getMainBuffer()->availForGet(_ca->getCallId());
// set available byte to maxByteToGet
int bytesAvail = (availBytesFromMic < maxBytesToGet) ? availBytesFromMic : maxBytesToGet;
// _debug("bytesAvail %i\n", bytesAvail);
if (bytesAvail == 0)
return 0;
......@@ -573,6 +583,7 @@ AudioRtpRTX::run ()
while (!testCancel()) {
// _debug("Main while loop for call: %s\n", _ca->getCallId().c_str());
// Send session
sessionWaiting = _session->isWaiting();
......
......@@ -222,6 +222,9 @@ class AudioRtpRTX : public ost::Thread, public ost::TimerPort {
/** The audio codec used during the session */
AudioCodec* _audiocodec;
/** Mutex */
ost::Mutex _rtpRtxMutex;
};
......@@ -281,7 +284,7 @@ class AudioRtp {
bool _symmetric;
/** Mutex */
ost::Mutex _threadMutex;
ost::Mutex _rtpMutex;
};
#endif // __AUDIO_RTP_H__
......@@ -301,7 +301,12 @@ int MainBuffer::availForPut(CallID call_id)
ost::MutexLock guard (_mutex);
return getRingBuffer(call_id)->AvailForPut();
RingBuffer* ringbuffer = getRingBuffer(call_id);
if (ringbuffer == NULL)
return 0;
else
return ringbuffer->AvailForPut();
}
......@@ -314,6 +319,9 @@ int MainBuffer::getData(void *buffer, int toCopy, unsigned short volume, CallID
CallIDSet* callid_set = getCallIDSet(call_id);
if(callid_set == NULL)
return 0;
if(callid_set->empty())
{
// _debug("CallIDSet with ID: \"%s\" is empty!\n", call_id.c_str());
......@@ -391,15 +399,17 @@ int MainBuffer::getDataByID(void *buffer, int toCopy, unsigned short volume, Cal
int MainBuffer::availForGet(CallID call_id)
{
// _debug("MainBuffer::availForGet\n");
ost::MutexLock guard (_mutex);
CallIDSet* callid_set = getCallIDSet(call_id);
if (callid_set == NULL)
return 0;
if (callid_set->empty())
{
// _debug("CallIDSet with ID: \"%s\" is empty!\n", call_id.c_str());
_debug("CallIDSet with ID: \"%s\" is empty!\n", call_id.c_str());
return 0;
}
......@@ -429,7 +439,12 @@ int MainBuffer::availForGet(CallID call_id)
int MainBuffer::availForGetByID(CallID call_id, CallID reader_id)
{
return getRingBuffer(call_id)->AvailForGet(reader_id);
RingBuffer* ringbuffer = getRingBuffer(call_id);
if (ringbuffer == NULL)
return 0;
else
return ringbuffer->AvailForGet(reader_id);
}
......@@ -442,6 +457,9 @@ int MainBuffer::discard(int toDiscard, CallID call_id)
CallIDSet* callid_set = getCallIDSet(call_id);
if (callid_set == NULL)
return 0;
if(callid_set->empty())
{
// _debug("CallIDSet with ID: \"%s\" is empty!\n", call_id.c_str());
......@@ -472,7 +490,12 @@ int MainBuffer::discard(int toDiscard, CallID call_id)
int MainBuffer::discardByID(int toDiscard, CallID call_id, CallID reader_id)
{
return getRingBuffer(call_id)->Discard(toDiscard, reader_id);
RingBuffer* ringbuffer = getRingBuffer(call_id);
if(ringbuffer == NULL)
return 0;
else
return ringbuffer->Discard(toDiscard, reader_id);
}
......@@ -486,6 +509,9 @@ void MainBuffer::flush(CallID call_id)
CallIDSet* callid_set = getCallIDSet(call_id);
if (callid_set == NULL)
return;
if(callid_set->empty())
{
// _debug("CallIDSet with ID: \"%s\" is empty!\n", call_id.c_str());
......@@ -520,5 +546,8 @@ void MainBuffer::flushDefault()
void MainBuffer::flushByID(CallID call_id, CallID reader_id)
{
getRingBuffer(call_id)->flush(reader_id);
RingBuffer* ringbuffer = getRingBuffer(call_id);
if(ringbuffer != NULL)
ringbuffer->flush(reader_id);
}
......@@ -40,6 +40,8 @@ PulseLayer::PulseLayer (ManagerImpl* manager)
_debug ("PulseLayer::Pulse audio constructor: Create context\n");
out_buffer = new SFLDataFormat[STATIC_BUFSIZE];
_urgentRingBuffer.createReadPointer();
}
// Destructor
......@@ -361,6 +363,7 @@ void PulseLayer::writeToSpeaker (void)
out_buffer[k] = 0;
if (urgentAvail > 0) {
// Urgent data (dtmf, incoming call signal) come first.
//_debug("Play urgent!: %i\e" , urgentAvail);
......@@ -396,6 +399,7 @@ void PulseLayer::writeToSpeaker (void)
} else {
// out = (SFLDataFormat*) pa_xmalloc (framesPerBuffer * sizeof (SFLDataFormat));
// _debug("PulseLayer::writeToSpeaker _mainBuffer.getData() toGet %i\n", toGet);
normalAvail = _mainBuffer.availForGet();
toGet = (normalAvail < (int) (framesPerBuffer * sizeof (SFLDataFormat))) ? normalAvail : framesPerBuffer * sizeof (SFLDataFormat);
......
......@@ -98,11 +98,19 @@ RingBuffer::getReadPointer(CallID call_id)
if(getNbReadPointer() == 0)
return 0;
// _debug("RingBuffer::getReadPointer() id %s\n", call_id.c_str());
ReadPointer::iterator iter = _readpointer.find(call_id);
if (iter == _readpointer.end())
{
_debug("RingBuffer::getReadPointer Error read pointer is null\n");
return NULL;
// _debug(" RingBuffer::getReadPointer Error read pointer size: %i\n", _readpointer.size());
// _debug(" RingBuffer::getReadPointer Error read pointer \"%s\" is null\n", call_id.c_str());
ReadPointer::iterator iter2;
for( iter2 = _readpointer.begin(); iter2 != _readpointer.end(); iter2++)
{
// x_debug(" RingBuffer::getReadPointer list avail pointer \"%s\"\n", iter2->first.c_str());
}
return 0;
}
else
{
......@@ -137,7 +145,7 @@ RingBuffer::storeReadPointer(int pointer_value, CallID call_id)
if(iter != _readpointer.end())
{
iter->second = pointer_value;
_debug("store read pointer call_id %s, size: %i \n",call_id.c_str(), _readpointer.size());
// _debug("store read pointer call_id %s, size: %i \n",call_id.c_str(), _readpointer.size());
}
else
{
......@@ -295,10 +303,8 @@ RingBuffer::Get (void *buffer, int toCopy, unsigned short volume, CallID call_id
dest = (samplePtr) buffer;
copied = 0;
int mStart = getReadPointer(call_id);
int mStart = getReadPointer(call_id);
//fprintf(stderr, "G");
while (toCopy) {
......
......@@ -43,6 +43,7 @@ void Conference::add(CallID participant_id)
_debug("---- Conference:: add participant %s\n", participant_id.c_str());
/*
if(_nbParticipant >= 1)
{
ParticipantSet::iterator iter;
......@@ -54,8 +55,8 @@ void Conference::add(CallID participant_id)
}
}
// Manager::instance().getAudioDriver()->getMainBuffer()->bindCallID(participant_id);
Manager::instance().getAudioDriver()->getMainBuffer()->bindCallID(participant_id);
*/
_participants.insert(participant_id);
_nbParticipant++;
......@@ -67,6 +68,7 @@ void Conference::remove(CallID participant_id)
_debug("---- Conference:: remove participant %s\n", participant_id.c_str());
/*
if(_nbParticipant >= 1)
{
ParticipantSet::iterator iter = _participants.begin();
......@@ -77,9 +79,33 @@ void Conference::remove(CallID participant_id)
Manager::instance().getAudioDriver()->getMainBuffer()->unBindCallID(participant_id, *iter);
}
}
*/
_participants.erase(participant_id);
_nbParticipant--;
}
void Conference::bindParticipant(CallID participant_id)
{
if(_nbParticipant >= 1)
{
ParticipantSet::iterator iter;
for(iter = _participants.begin(); iter != _participants.end(); iter++)
{
if (participant_id != (*iter))
{
_debug("---- Conference:: bind callid %s with %s in conference add\n", participant_id.c_str(), (*iter).c_str());
Manager::instance().getAudioDriver()->getMainBuffer()->bindCallID(participant_id, *iter);
}
}
}
_debug("---- Conference:: bind callid %s with default_id in conference add\n", participant_id.c_str());
Manager::instance().getAudioDriver()->getMainBuffer()->bindCallID(participant_id);
}
......@@ -43,6 +43,8 @@ class Conference{
void remove(CallID participant_id);
void bindParticipant(CallID participant_id);
private:
/** Unique ID of the call */
......
......@@ -369,9 +369,6 @@ ManagerImpl::hangupCall (const CallID& id)
if (! (nbCalls > 1))
audiolayer->stopStream();
if(participToConference(id))
removeParticipant(id);
/* Direct IP to IP call */
if (getConfigFromCall (id) == Call::IPtoIP) {
returnValue = SIPVoIPLink::instance (AccountNULL)->hangup (id);
......@@ -392,6 +389,9 @@ ManagerImpl::hangupCall (const CallID& id)
removeCallAccount (id);
}
if(participToConference(id))
removeParticipant(id);
switchCall ("");
if (_audiodriver->getLayerType() == PULSEAUDIO && getConfigInt (PREFERENCES , CONFIG_PA_VOLUME_CTRL)) {
......@@ -650,8 +650,6 @@ ManagerImpl::createConference(const CallID& id)
conf->add(getCurrentCallId());
conf->add(id);
answerCall(id);
}
void
......@@ -705,6 +703,9 @@ ManagerImpl::addParticipant(const CallID& call_id)
{
_debug("NO CONFERENCE YET, CREATE ONE\n");
createConference(call_id);
answerCall(call_id);
}
else
{
......@@ -747,6 +748,25 @@ ManagerImpl::removeParticipant(const CallID& call_id)
}
}
void
ManagerImpl::addStream(const CallID& call_id)
{
_debug("ManagerImpl::addStream %s\n", call_id.c_str());
if(participToConference(call_id))
{
ConferenceMap::iterator iter = _conferencemap.find(default_conf);
Conference* conf = iter->second;
conf->bindParticipant(call_id);
}
else
{
getAudioDriver()->getMainBuffer()->bindCallID(call_id);
}
}
//THREAD=Main
bool
ManagerImpl::saveConfig (void)
......
......@@ -196,6 +196,8 @@ class ManagerImpl {
void removeParticipant(const CallID& call_id);
void addStream(const CallID& call_id);
/**
* Save config to file
* @return true on success
......@@ -1162,8 +1164,10 @@ class ManagerImpl {
int isStunEnabled (void);
void enableStun (void);
// Map
ConferenceCallMap _conferencecall;
//
ConferenceMap _conferencemap;
private:
......
......@@ -39,7 +39,8 @@ SIPCall::SIPCall (const CallID& id, Call::CallType type, pj_pool_t *pool) : Call
SIPCall::~SIPCall()
{
delete _audiortp;
_audiortp = 0;
delete _local_sdp;
_local_sdp = 0;
_debug ("SIPCALL::Destructor for this class is called \n");
......
......@@ -734,7 +734,7 @@ SIPVoIPLink::hangup (const CallID& id)
// Release RTP thread
if (Manager::instance().isCurrentCall (id)) {
_debug ("* SIP Info: Stopping AudioRTP for hangup\n");
_debug ("* SIP Info: Stopping AudioRTP for hangup %s\n", call->getCallId().c_str());
call->getAudioRtp()->closeRtpSession();
}
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment