[prev in list] [next in list] [prev in thread] [next in thread]
List: helix-server-cvs
Subject: [Server-cvs] engine/core source_container.cpp, 1.8,
From: ckarusala () helixcommunity ! org
Date: 2011-11-24 4:53:23
[Download RAW message or body]
Update of /cvsroot/server/engine/core
In directory cvs01.internal.helixcommunity.org:/tmp/cvs-serv23276
Modified Files:
source_container.cpp static_source_container.cpp
Log Message:
Synopsis
========
This CR contains changes for the iOS Closed Caption support and numerous updates & \
fixes for multi-track.
Branch : SERVER_14_2_RN, HEAD
Suggested Reviewer : Sujeet, Dean
Description:
==========
This CR adds the support for multi-language closed captions to HLS packetization and \
streaming in server. The closed caption tracks "clcp" tracks are read from the mp4 \
fileformat, packetized as H264 SEI NAL units, merged with H264 elementary stream, \
packetized into TS and written to the segments. Closed captions are only supported \
for VOD and for HLS only. Users will be able to choose the required CC stream using \
the query paramter "cc" (configurable) in the HLS URLs. Below are the details about \
this feature and the additional updates & fixes made in general to multi-track \
feature as per the new specs.
mp4fileformat: Updated the mp4fileformat to read "clcp" tracks from ISO files, these \
are only read if the packetization is "pes" (for HLS) and are ignored for RTSP and \
RTMP packetizations. Updated the private class factory to create a "pes" packetizer \
that will handle the "clcp" track data.
mpeg pes payload updates : Added a new packetizer (CH264CCPayload), which will take \
the closed caption track data and construct H264 SEI NAL units out of it as per the \
packet format specified in 14496-10, ATSC-53/Part 4, ATSC-72 Part 1 specs. Also \
updated the h264 pes packetizer to add SPS-PPS only if it is not already present. And \
AUD NAL should be added before adding the SPS-PPS NAL. Corrected that.
mpeg2 file writer: Updated the filewriter to handle the live archiving for \
multi-track live and create correct segment library names for each of the audio-video \
combinations. Added a new line at the end of the VOD playlist which was missing \
before. Updated the writer to handle multiple videos (as opposed to single video as \
was done before). Now when there are more than one streams of same type and name, \
they will be made as part of a multi-rate presentations. Bitrate query parameters are \
not necessary for HLS. Updated the multitrack wrapper class to handle multiple videos \
with the same name (similar to how audio were handled) and construct multirate \
presentations. This wrapper class will only handle live streams now. It pairs up each \
unique audio with each unique video and comes up with all the possible SR/MR \
presentations, creates the mappings, writers and pass the TS packets to writers.
tsmuxer changes: Updated TS muxer to ignore the stream headers for CC tracks as the \
packets from the CC tracks do not reach the muxer. They are merged with video data \
earlier. So muxer should not be listing the CC stream as a independent stream in the \
program specific information (PSI) tables.
m3ugen changes: Updated m3ugen to ignore video bitrate query parameter. It will now \
look for CC QP for VOD requests. Also, while sending packetization requests to \
mpeg2ts plugin, it will now send the complete URL with QPs for VOD cases so that the \
mpeg2ts plugin knows which streams to segment. And m3ugen takes the final M3U8 \
filename from the mpeg2ts plugin since what is created can be different due to \
(un)availability of different streams selected in URL QPs. Also updated the m3ugen to \
look for MDAT file to determine if VOD content is completely segmented instead of the \
earlier logic of opening playlists and looking for END tags.
mpeg2ts plugin: Major changes are made to CStreamHandler class. It will now segment \
only the requested combinations for VOD content as opposed to all. It will determine \
if the content is a mulit-track request or not by looking at the mountpoint name for \
live and the presence of MP QPs for VOD. We don't need the special "Helix MT Content" \
string anymore in the "Title" of the VOD content. Cleanup of the live playlists at \
the end of the segmentation was failing for MT live since the playlist/segment \
library names will have extensions based on the video/audio stream names. Added a \
list to keep track of all the extensions and used it to cleanup at the end. Stream \
handler now uses the CMultiplexerURLParser class to determine if the multiplexing is \
enabled and what the streams are selected in the URL QPs. It has been updated to \
handle the CC streams for VOD content. A new helper class CCMerger is created to \
merge the closed catpion packets into H264 PES packets. Only one CC stream will be \
active at a time. A CCMerger class is created for each of the active video streams. \
And both the video packets and the CC packets are passed to the CCMerger class which \
will merge and output new packets.
ccmerger: Helper class to merge cc packets (containing H264 SEI NAL
units) and the H264 Video packets.
rtmpserver: Multi-track URL parsing is happening at a wrong place resulting in always \
streaming a video and audio even though wrong streamnames are speicifed in the MT \
QPs. Corrected that.
source_container : Current call flow of initializing the source causing issues in \
BroadcastStreamer causing it think the sinks are MDP sinks when they are not. \
Adjusted the flow to correct that.
static_source_container : This class maintain an array for GetPacketCallbacks for \
each of the streams on which StartPackets() is called, but the total number of \
streams it counts is the total number of StartPackets() calls made on it. This is \
causing problems when StartPackets() is called on, for example, stream 3 & 4. In this \
case it is trying to reference indexes 0 & 1 for these streams. Converted the array \
into a map.
mpurlparser: Updated to
1. Handle and match Language in addition to just the StreamName.
2. Handle CC query parameter.
3. Return multi-trate streams for HLS cases.
4. Handle "default" for vid, aud & cc QPs.
livemultiplexer : Updated it to not write/append the special string "Helix MT \
Content" to the "Title" of the presentation.
Files New
=========
datatype_rn/mpeg2/payload/h264ccpespyld.cpp
datatype_rn/mpeg2/payload/pub/h264ccpespyld.h
server_rn/datatype/mpeg2ts/ccmerge.cpp
server_rn/datatype/mpeg2ts/pub/ccmerge.h
Files Modified
==========
datatype/mp4/fileformat/qtatmmgs.cpp
datatype/mp4/fileformat/qttrack.cpp
datatype/mp4/fileformat/pub/qtatmmgs.h
datatype/mp4/fileformat/pub/qtatoms.h
datatype_rn/mp4/fileformat/qtpluspacketizerfct.cpp
datatype_rn/mpeg2/payload/Umakefil
datatype_rn/mpeg2/payload/h264pespyld.cpp
datatype_rn/mpeg2/ts/filewriter/ctsarchiver.cpp
datatype_rn/mpeg2/ts/filewriter/mpeg2tsfwrtr.cpp
datatype_rn/mpeg2/ts/filewriter/multitrackwrapper.cpp
datatype_rn/mpeg2/ts/filewriter/pub/mpeg2tsfwrtr.h
datatype_rn/mpeg2/ts/filewriter/pub/multitrackwrapper.h
datatype_rn/mpeg2/ts/filewriter/pub/playlistgen.h
datatype_rn/mpeg2/ts/muxer/tsmux.cpp
datatype_rn/mpeg2/ts/muxer/pub/tsmux.h
server_rn/appext/m3ugen/m3ugenfsys.cpp
server_rn/datatype/mpeg2ts/Umakefil
server_rn/datatype/mpeg2ts/mpeg2tsplin.cpp
server_rn/datatype/mpeg2ts/streamhandler.cpp
server_rn/datatype/mpeg2ts/pub/streamhandler.h
server_rn/protocol/flash/rtmpserv/rtmpserv.cpp
server/engine/core/source_container.cpp
server/engine/core/static_source_container.cpp
server/engine/core/pub/static_source_container.h
server/protocol/common/mp_url_parser.cpp
server/protocol/common/pub/mp_url_parser.h
server-restricted/broadcast/app/multiplexer/livemultiplexer.cpp
Testing Performed
=================
Unit Tests:
- Tested various content SR/MR with mutliple variations of number and type of \
streams. Verified cc streams in both SR and MR. Playback to IPad is verified for \
various combinations selected in the URLs. Verified live archiving is working for \
HLS.
Integration Tests:
- None.
Leak Tests:
- Verified that no major leaks are added.
Performance Tests:
- None
Platforms Tested: linux-rhel5-x86_64
Build Verified: linux-rhel5-x86_64
Thanks,
Chytanya
Index: static_source_container.cpp
===================================================================
RCS file: /cvsroot/server/engine/core/static_source_container.cpp,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -d -r1.6 -r1.7
--- static_source_container.cpp 12 Nov 2009 00:47:45 -0000 1.6
+++ static_source_container.cpp 24 Nov 2011 04:53:20 -0000 1.7
@@ -40,6 +40,7 @@
#include "hxtypes.h"
#include "hxcom.h"
#include "hxengin.h"
+#include "chxmaplongtoobj.h"
#include "static_source_container.h"
#include "hxassert.h"
#include "timeval.h"
@@ -47,22 +48,17 @@
StaticSourceContainer::StaticSourceContainer(IUnknown* pContext,
IHXPSourceControl* pSourceControl)
- : m_bReady(FALSE)
- , m_bPacketsStarted(FALSE)
+ : m_bPacketsStarted(FALSE)
, m_bAdvanceSchedulerTime(FALSE)
, m_bOneStreamStarted(FALSE)
- , m_bGetPacketOutstanding(FALSE)
, m_bDone(FALSE)
, m_lRefCount(0)
- , m_ulStopPacketsSeen(0)
- , m_nStreamCount(0)
-
, m_pSourcePackets(NULL)
, m_pScheduler(NULL)
, m_pThreadSafeScheduler(NULL)
, m_pSink(NULL)
- , m_ppPacketStreams(NULL)
+ , m_pPacketStreams(NULL)
, m_pContext(pContext)
, m_pSourceControl(pSourceControl)
@@ -86,6 +82,8 @@
HX_VERIFY(HXR_OK == pSourceControl->QueryInterface(IID_IHXPSourcePackets,
(void **)&m_pSourcePackets));
}
+
+ m_pPacketStreams = new CHXMapLongToObj();
}
StaticSourceContainer::~StaticSourceContainer()
@@ -105,18 +103,24 @@
HX_RELEASE(m_pSink);
}
- if (m_ppPacketStreams)
+ if (m_pPacketStreams)
{
- for (UINT32 i = 0; i < m_nStreamCount; i++)
- {
- if (m_ppPacketStreams [i]->m_Handle)
- {
- m_pThreadSafeScheduler->Remove(m_ppPacketStreams[i]->m_Handle);
- }
+ CHXMapLongToObj::Iterator it;
+ for (it = m_pPacketStreams->Begin(); it != m_pPacketStreams->End(); it++)
+ {
+ GetPacketCallback* pGetPacketCallback = (GetPacketCallback*)(*it);
- HX_RELEASE(m_ppPacketStreams [i]);
- }
- HX_VECTOR_DELETE(m_ppPacketStreams);
+ if (pGetPacketCallback && pGetPacketCallback->m_Handle && \
m_pThreadSafeScheduler) + {
+ m_pThreadSafeScheduler->Remove(pGetPacketCallback->m_Handle);
+ pGetPacketCallback->m_Handle = 0;
+ }
+
+ HX_RELEASE(pGetPacketCallback);
+ }
+
+ m_pPacketStreams->RemoveAll();
+ HX_DELETE(m_pPacketStreams);
}
HX_RELEASE(m_pScheduler);
@@ -245,17 +249,25 @@
m_bDone = TRUE;
- for (UINT32 i = 0; i < m_nStreamCount; i++)
+ if (m_pPacketStreams)
{
- if ( (m_ppPacketStreams) && (m_ppPacketStreams [i]) &&
- (m_ppPacketStreams [i]->m_Handle) )
- {
- m_pThreadSafeScheduler->Remove(m_ppPacketStreams[i]->m_Handle);
- }
+ CHXMapLongToObj::Iterator it;
+ for (it = m_pPacketStreams->Begin(); it != m_pPacketStreams->End(); it++)
+ {
+ GetPacketCallback* pGetPacketCallback = (GetPacketCallback*)(*it);
- HX_RELEASE(m_ppPacketStreams [i]);
+ if (pGetPacketCallback && pGetPacketCallback->m_Handle && \
m_pThreadSafeScheduler) + {
+ m_pThreadSafeScheduler->Remove(pGetPacketCallback->m_Handle);
+ pGetPacketCallback->m_Handle = 0;
+ }
+
+ HX_RELEASE(pGetPacketCallback);
+ }
+
+ m_pPacketStreams->RemoveAll();
+ HX_DELETE(m_pPacketStreams);
}
- HX_VECTOR_DELETE(m_ppPacketStreams);
if (m_pSourceControl)
{
@@ -306,10 +318,15 @@
m_pSink->PacketReady(HXR_OK, pPacket);
+ GetPacketCallback* pGetPacketCallback = NULL;
+ m_pPacketStreams->Lookup(uStreamNo, (REF(void*))pGetPacketCallback);
+
+ HX_ASSERT(pGetPacketCallback);
+
if (0 == m_ulBandWidthFactor)
{
- m_ppPacketStreams[uStreamNo]->m_pTimeToSchedule = \
m_pScheduler->GetCurrentSchedulerTime();
- m_ppPacketStreams[uStreamNo]->ScheduleNextPacket();
+ pGetPacketCallback->m_pTimeToSchedule = \
m_pScheduler->GetCurrentSchedulerTime(); + \
pGetPacketCallback->ScheduleNextPacket(); }
else
{
@@ -349,9 +366,9 @@
tPacket -= m_SchedulerTimeOffset;
}
- m_ppPacketStreams[uStreamNo]->m_pTimeToSchedule.tv_sec = \
tPacket.tv_sec;
- m_ppPacketStreams[uStreamNo]->m_pTimeToSchedule.tv_usec = \
tPacket.tv_usec;
- m_ppPacketStreams[uStreamNo]->ScheduleNextPacket();
+ pGetPacketCallback->m_pTimeToSchedule.tv_sec = tPacket.tv_sec;
+ pGetPacketCallback->m_pTimeToSchedule.tv_usec = tPacket.tv_usec;
+ pGetPacketCallback->ScheduleNextPacket();
}
else
{
@@ -366,26 +383,10 @@
STDMETHODIMP
StaticSourceContainer::StartPackets(UINT16 unStreamNumber)
{
- /* this class never sees the stream headers
- * so we need to grow the vector of
- * GetPackeCallbacks as needed.
- */
- m_nStreamCount++;
-
- GetPacketCallback** pOld = m_ppPacketStreams;
-
- m_ppPacketStreams = new GetPacketCallback* [m_nStreamCount];
- memset(m_ppPacketStreams, 0, sizeof(GetPacketCallback*) * m_nStreamCount);
-
- if (pOld != NULL)
- {
- memcpy(m_ppPacketStreams, pOld, sizeof(GetPacketCallback*) * (m_nStreamCount-1));
- }
-
- HX_VECTOR_DELETE(pOld);
+ GetPacketCallback* pGetPacketCallback = new GetPacketCallback (this, \
unStreamNumber); + pGetPacketCallback->AddRef();
- m_ppPacketStreams [unStreamNumber] = new GetPacketCallback (this, \
unStreamNumber);
- m_ppPacketStreams [unStreamNumber]->AddRef();
+ m_pPacketStreams->SetAt(unStreamNumber, (void*)pGetPacketCallback);
/* Setup timing adjustments for GetPacket scheduling */
if(!m_bOneStreamStarted)
@@ -414,7 +415,7 @@
}
/* start the flow of packets */
- m_ppPacketStreams[unStreamNumber]->m_bPacketsStarted = m_bPacketsStarted = TRUE;
+ pGetPacketCallback->m_bPacketsStarted = m_bPacketsStarted = TRUE;
m_pSourcePackets->GetPacket(unStreamNumber);
@@ -425,15 +426,25 @@
StaticSourceContainer::StopPackets(UINT16 unStreamNumber)
{
m_bPacketsStarted = FALSE;
+ m_bOneStreamStarted = FALSE;
- if ( (m_ppPacketStreams) && (m_ppPacketStreams [unStreamNumber]) )
+ if (m_pPacketStreams)
{
- if (m_ppPacketStreams [unStreamNumber]->m_Handle)
- {
- m_pThreadSafeScheduler->Remove(m_ppPacketStreams \
[unStreamNumber]->m_Handle);
- }
+ GetPacketCallback* pGetPacketCallback = NULL;
+ m_pPacketStreams->Lookup(unStreamNumber, (REF(void*))pGetPacketCallback);
- m_ppPacketStreams [unStreamNumber]->m_bPacketsStarted = FALSE;
+ if (pGetPacketCallback)
+ {
+ if (pGetPacketCallback->m_Handle && m_pThreadSafeScheduler)
+ {
+ m_pThreadSafeScheduler->Remove(pGetPacketCallback->m_Handle);
+ pGetPacketCallback->m_Handle = 0;
+ }
+
+ pGetPacketCallback->m_bPacketsStarted = FALSE;
+ m_pPacketStreams->RemoveKey(unStreamNumber);
+ HX_RELEASE(pGetPacketCallback);
+ }
}
return HXR_OK;
Index: source_container.cpp
===================================================================
RCS file: /cvsroot/server/engine/core/source_container.cpp,v
retrieving revision 1.8
retrieving revision 1.9
diff -u -d -r1.8 -r1.9
--- source_container.cpp 26 Sep 2011 19:54:23 -0000 1.8
+++ source_container.cpp 24 Nov 2011 04:53:20 -0000 1.9
@@ -160,26 +160,27 @@
* we could be released... so AddRef ourselves
*/
AddRef();
- h_result = m_pSourceControl->Init((IHXPSinkControl*)m_pSink);
+
+ if (m_pSourceLivePackets)
+ {
+ h_result = m_pSourceLivePackets->Init(this);
- if (HXR_OK == h_result)
- {
- if (m_pSourceLivePackets)
+ if (h_result == HXR_OK)
+ {
+ h_result = m_pSourceControl->Init((IHXPSinkControl*)m_pSink);
+ }
+ if (HXR_OK == h_result)
{
- h_result = m_pSourceLivePackets->Init(this);
-
- if (HXR_OK == h_result)
- {
goto InitOK;
- }
- }
- else
- {
- // if there are no source packets, we must be done
- // so, proceed without error.
- goto InitOK;
}
- }
+ }
+ else
+ {
+ // if there are no source packets, we must be done
+ // so, proceed without error.
+ goto InitOK;
+ }
+
m_pSink->Release();
m_pSink = 0;
_______________________________________________
Server-cvs mailing list
Server-cvs@helixcommunity.org
http://lists.helixcommunity.org/mailman/listinfo/server-cvs
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic