Adds utility methods to RawPacket that allow setting and extracting a list of CSRC identifiers. Changes storage of SSRC id-s to long rather than String to optimize their insertion in RTP packets as well as garbage collection

cusax-fix
Emil Ivov 16 years ago
parent 99da055f88
commit e479dcce1c

@ -17,6 +17,8 @@
import javax.media.rtp.*;
import javax.media.rtp.event.*;
import com.sun.media.rtp.*;
import net.java.sip.communicator.impl.neomedia.device.*;
import net.java.sip.communicator.impl.neomedia.format.*;
import net.java.sip.communicator.impl.neomedia.transform.*;
@ -129,12 +131,18 @@ public class MediaStreamImpl
/**
* The SSRC identifier of the party that we are exchanging media with.
*/
private String remoteSourceID = null;
private long remoteSourceID = -1;
/**
* Our own SSRC identifier.
*/
private String localSourceID = null;
private long localSourceID = -1;
/**
* The list of CSRC IDs that the remote party reported as contributing to
* the media they are sending toward us.
*/
private long[] remoteContributingSourceIDList = new long[0];
/**
* The indicator which determines whether this <tt>MediaStream</tt> is set
@ -164,6 +172,8 @@ public MediaStreamImpl(StreamConnector connector, MediaDevice device)
setDevice(device);
this.rtpConnector = new RTPTransformConnector(connector);
}
/**
@ -419,8 +429,7 @@ public MediaDirection getDirection()
MediaDeviceSession deviceSession = getDeviceSession();
return
(deviceSession == null)
return (deviceSession == null)
? MediaDirection.INACTIVE
: deviceSession.getDevice().getDirection();
}
@ -445,8 +454,7 @@ public Map<Byte, MediaFormat> getDynamicRTPPayloadTypes()
{
synchronized (dynamicRTPPayloadTypes)
{
return
new HashMap<Byte, MediaFormat>(dynamicRTPPayloadTypes);
return new HashMap<Byte, MediaFormat>(dynamicRTPPayloadTypes);
}
}
@ -465,16 +473,15 @@ public MediaFormat getFormat()
/**
* Gets the synchronization source (SSRC) identifier of the local peer or
* <tt>null</tt> if it is not yet known.
* <tt>-1</tt> if it is not yet known.
*
* @return the synchronization source (SSRC) identifier of the local peer
* or <tt>null</tt> if it is not yet known
* or <tt>-1</tt> if it is not yet known
* @see MediaStream#getLocalSourceID()
*/
public String getLocalSourceID()
public long getLocalSourceID()
{
// TODO Auto-generated method stub
return null;
return this.localSourceID;
}
/**
@ -486,8 +493,7 @@ public String getLocalSourceID()
*/
public InetSocketAddress getRemoteControlAddress()
{
return
(InetSocketAddress)
return (InetSocketAddress)
rtpConnector.getControlSocket().getRemoteSocketAddress();
}
@ -500,20 +506,19 @@ public InetSocketAddress getRemoteControlAddress()
*/
public InetSocketAddress getRemoteDataAddress()
{
return
(InetSocketAddress)
return (InetSocketAddress)
rtpConnector.getDataSocket().getRemoteSocketAddress();
}
/**
* Get the synchronization source (SSRC) identifier of the remote peer or
* <tt>null</tt> if it is not yet known.
* <tt>-1</tt> if it is not yet known.
*
* @return the synchronization source (SSRC) identifier of the remote
* peer or <tt>null</tt> if it is not yet known
* peer or <tt>-1</tt> if it is not yet known
* @see MediaStream#getRemoteSourceID()
*/
public String getRemoteSourceID()
public long getRemoteSourceID()
{
return remoteSourceID;
}
@ -579,9 +584,7 @@ private RTPManager getRTPManager()
//JMF inits the local SSRC upon initialize(RTPConnector) so now's
//the time to ask:
setLocalSourceID(Long.toHexString(
(((com.sun.media.rtp.RTPSessionMgr)
rtpManager).getLocalSSRC())));
setLocalSourceID(((RTPSessionMgr)rtpManager).getLocalSSRC());
createSendStreams();
}
@ -1256,7 +1259,7 @@ public void update(ReceiveStreamEvent event)
logger.trace("Received new ReceiveStream with ssrc "
+ receiveStream.getSSRC());
setRemoteSourceID( Long.toHexString( receiveStream.getSSRC() ));
setRemoteSourceID( receiveStream.getSSRC() );
synchronized (receiveStreams)
{
@ -1326,9 +1329,9 @@ public void update(SessionEvent event)
* @param ssrc the SSRC identifier that this stream will be using in
* outgoing RTP packets from now on.
*/
private void setLocalSourceID(String ssrc)
private void setLocalSourceID(long ssrc)
{
String oldValue = this.localSourceID;
Long oldValue = this.localSourceID;
this.localSourceID = ssrc;
firePropertyChange(PNAME_LOCAL_SSRC, oldValue, ssrc);
@ -1341,11 +1344,64 @@ private void setLocalSourceID(String ssrc)
* @param ssrc the SSRC identifier that this stream will be using in
* outgoing RTP packets from now on.
*/
private void setRemoteSourceID(String ssrc)
private void setRemoteSourceID(long ssrc)
{
String oldValue = this.remoteSourceID;
Long oldValue = this.remoteSourceID;
this.remoteSourceID = ssrc;
firePropertyChange(PNAME_REMOTE_SSRC, oldValue, ssrc);
}
/**
* Returns the list of CSRC identifiers for all parties currently known
* to contribute to the media that this stream is sending toward its remote
* counter part. In other words, the method returns the list of CSRC IDs
* that this stream will include in outgoing RTP packets. This method will
* return an empty <tt>List</tt> in case this stream is not part of a mixed
* conference call.
*
* @return a <tt>List</tt> of CSRC IDs for parties that are currently known
* to contribute to the media that this stream is currently streaming or
* an empty <tt>List</tt> in case this <tt>MediaStream</tt> is not part of
* a conference call.
*/
public List<String> getLocalContributingSourceIDs()
{
List<String> csrcList = new ArrayList<String>();
MediaDeviceSession deviceSession = getDeviceSession();
if( this.deviceSession != null)
csrcList.addAll( deviceSession.getRemoteSSRCList() );
Iterator<String> csrcIter = csrcList.iterator();
//in case of a conf call the mixer would return all SSRC IDs that are
//currently contributing including this stream's counterpart. This
//method is about
while(csrcIter.hasNext())
{
String csrc = csrcIter.next();
if (csrc.equals(getRemoteSourceID()))
csrcIter.remove();
}
return csrcList;
}
/**
* Returns the <tt>List</tt> of CSRC identifiers representing the parties
* contributing to the stream that we are receiving from this
* <tt>MediaStream</tt>'s remote party.
*
* @return a <tt>List</tt> of CSRC identifiers representing the parties
* contributing to the stream that we are receiving from this
* <tt>MediaStream</tt>'s remote party.
*/
public List<String> getRemoteContributingSourceIDs()
{
List<String> csrcList = new ArrayList<String>();
return csrcList;
}
}

@ -6,6 +6,9 @@
*/
package net.java.sip.communicator.impl.neomedia;
import java.math.*;
import java.util.*;
/**
* When using TransformConnector, a RTP/RTCP packet is represented using
* RawPacket. RawPacket stores the buffer holding the RTP/RTCP packet, as well
@ -19,6 +22,7 @@
*
* @author Werner Dittmann (Werner.Dittmann@t-online.de)
* @author Bing SU (nova.su@gmail.com)
* @author Emil Ivov
*/
public class RawPacket
{
@ -39,6 +43,11 @@ public class RawPacket
*/
protected int length;
/**
* The size of the fixed part of the RTP header as defined by RFC 3550.
*/
public static final int FIXED_HEADER_SIZE = 12;
/**
* Construct a RawPacket using specified value.
*
@ -237,4 +246,100 @@ public void shrink(int len)
this.length = 0;
}
}
/**
* Returns the number of CSRC identifiers currently included in this packet.
*
* @return the CSRC count for this <tt>RawPacket</tt>.
*/
public int getCsrcCount()
{
return (buffer[offset] & 0x0fb);
}
/**
* Replaces the existing CSRC list (even if empty) with <tt>newCsrcList</tt>
* and updates the CC (CSRC count) field of this <tt>RawPacket</tt>
* accordingly.
*
* @param newCsrcList the list of CSRC identifiers that we'd like to set for
* this <tt>RawPacket</tt>.
*/
public void setCsrcList(long[] newCsrcList)
{
int newCsrcCount = newCsrcList.length;
byte[] csrcBuff = new byte[newCsrcCount * 4];
int csrcOffset = 0;
for(long csrc : newCsrcList)
{
csrcBuff[csrcOffset] = (byte)(csrc >> 24);
csrcBuff[csrcOffset+1] = (byte)(csrc >> 16);
csrcBuff[csrcOffset+2] = (byte)(csrc >> 8);
csrcBuff[csrcOffset+3] = (byte)csrc;
csrcOffset += 4;
}
int oldCsrcCount = getCsrcCount();
byte[] oldBuffer = this.getBuffer();
//the new buffer needs to be bigger than the new one in order to
//accommodate the list of CSRC IDs (unless there were more of them
//previously than after setting the new list).
byte[] newBuffer
= new byte[oldBuffer.length + csrcBuff.length - oldCsrcCount*4];
//copy the part up to the CSRC list
System.arraycopy(
oldBuffer, 0, newBuffer, 0, offset + FIXED_HEADER_SIZE);
//copy the new CSRC list
System.arraycopy( csrcBuff, 0, newBuffer,
offset + FIXED_HEADER_SIZE, csrcBuff.length);
//now copy the payload from the old buff and make sure we don't copy
//the CSRC list if there was one in the old packet
int payloadOffsetForOldBuff
= offset + FIXED_HEADER_SIZE + oldCsrcCount*4;
int payloadOffsetForNewBuff
= offset + FIXED_HEADER_SIZE + newCsrcCount*4;
System.arraycopy( oldBuffer, payloadOffsetForOldBuff,
newBuffer, payloadOffsetForNewBuff,
csrcBuff.length - payloadOffsetForOldBuff);
//set the new CSRC count
newBuffer[offset] = (byte)((newBuffer[offset] & 0xF0b)
& newCsrcCount);
}
/**
* Returns the list of CSRC IDs, currently encapsulated in this packet.
*
* @return an array containing the list of CSRC IDs, currently encapsulated
* in this packet.
*/
public long[] extractCsrcList()
{
int csrcCount = getCsrcCount();
byte[] buffer = getBuffer();
long[] csrcList = new long[csrcCount];
int csrcStartIndex = offset + FIXED_HEADER_SIZE;
for (int i = 0; i < csrcCount; i++)
{
csrcList[i] = buffer[csrcStartIndex] << 24
& buffer[csrcStartIndex + 1] << 16
& buffer[csrcStartIndex + 2] << 8
& buffer[csrcStartIndex + 3];
csrcStartIndex += 4;
}
return csrcList;
}
}

@ -116,7 +116,10 @@ public RawPacket transform(RawPacket pkt)
? engine.getRTPTransformer()
: engine.getRTCPTransformer();
pkt = pTransformer.transform(pkt);
//the packet transformer may be null if for example the engine
//only does RTP transformations and this is an RTCP transformer.
if( pTransformer != null)
pkt = pTransformer.transform(pkt);
}
return pkt;
@ -144,7 +147,10 @@ public RawPacket reverseTransform(RawPacket pkt)
? engine.getRTPTransformer()
: engine.getRTCPTransformer();
pkt = pTransformer.reverseTransform(pkt);
//the packet transformer may be null if for example the engine
//only does RTP transformations and this is an RTCP transformer.
if( pTransformer != null)
pkt = pTransformer.reverseTransform(pkt);
}
return pkt;

@ -626,7 +626,7 @@ private void getMediaXML(CallPeerSipImpl callPeer, StringBuffer xml)
// </type>
append(xml, "</", ELEMENT_TYPE, ">");
String srcId = stream.getRemoteSourceID();
String srcId = Long.toString(stream.getRemoteSourceID());
if (srcId != null)
{

@ -97,25 +97,25 @@ public interface MediaStream
/**
* Returns the synchronization source (SSRC) identifier of the remote
* participant or <tt>null</tt> if that identifier is not yet known at this
* participant or <tt>-1</tt> if that identifier is not yet known at this
* point.
*
* @return the synchronization source (SSRC) identifier of the remote
* participant or <tt>null</tt> if that identifier is not yet known at this
* participant or <tt>-1</tt> if that identifier is not yet known at this
* point.
*/
public String getRemoteSourceID();
public long getRemoteSourceID();
/**
* Returns the synchronization source (SSRC) identifier of the local
* participant or <tt>null</tt> if that identifier is not yet known at this
* participant or <tt>-1</tt> if that identifier is not yet known at this
* point.
*
* @return the synchronization source (SSRC) identifier of the local
* participant or <tt>null</tt> if that identifier is not yet known at this
* participant or <tt>-1</tt> if that identifier is not yet known at this
* point.
*/
public String getLocalSourceID();
public long getLocalSourceID();
/**
* Returns the address that this stream is sending RTCP traffic to.

Loading…
Cancel
Save