EBML updates:

- AV1 support
- Support for outputting fragments longer than 30 seconds in duration
- Fixed FireFox support for Opus audio tracks
- Added support for stdin live input of EBML
- Fixed broken timestamps when seeking in VoD EBML files
- Analyser now calculates offsets for (manual) double-checking
- Added JSON track support to EBML input and output
- Added basic input support for SRT/ASS/SSA subtitles
- Opus CODECDELAY now actually calculated.
- Fixed Opus in Firefox
- Improved MP3 support, more robust handling of corruption, support for non-standard timescale sources

# Conflicts:
#	src/output/output_ebml.cpp
This commit is contained in:
Thulinma 2018-07-20 14:23:34 +02:00
parent f8e9904e4e
commit 14427f0167
8 changed files with 348 additions and 91 deletions

View file

@ -8,6 +8,8 @@ void AnalyserEBML::init(Util::Config &conf){
AnalyserEBML::AnalyserEBML(Util::Config &conf) : Analyser(conf){
curPos = prePos = 0;
lastSeekId = 0;
lastSeekPos = 0;
}
bool AnalyserEBML::parsePacket(){
@ -15,11 +17,18 @@ bool AnalyserEBML::parsePacket(){
// Read in smart bursts until we have enough data
while (isOpen() && dataBuffer.size() < neededBytes()){
uint64_t needed = neededBytes();
if (needed > 1024*1024){
dataBuffer.erase(0, 1);
continue;
}
dataBuffer.reserve(needed);
for (uint64_t i = dataBuffer.size(); i < needed; ++i){
dataBuffer += std::cin.get();
++curPos;
if (!std::cin.good()){dataBuffer.erase(dataBuffer.size() - 1, 1);}
if (!std::cin.good()){
dataBuffer.erase(dataBuffer.size() - 1, 1);
return false;
}
}
}
@ -28,6 +37,33 @@ bool AnalyserEBML::parsePacket(){
EBML::Element E(dataBuffer.data(), true);
HIGH_MSG("Read an element at position %d", prePos);
if (detail >= 2){std::cout << E.toPrettyString(depthStash.size() * 2, detail);}
switch (E.getID()){
case EBML::EID_SEGMENT:
segmentOffset = prePos + E.getHeaderLen();
std::cout << "[OFFSET INFORMATION] Segment offset is " << segmentOffset << std::endl;
break;
case EBML::EID_CLUSTER:
std::cout << "[OFFSET INFORMATION] Cluster at " << (prePos-segmentOffset) << std::endl;
break;
case EBML::EID_SEEKID:
lastSeekId = E.getValUInt();
break;
case EBML::EID_SEEKPOSITION:
lastSeekPos = E.getValUInt();
break;
case EBML::EID_INFO:
case EBML::EID_TRACKS:
case EBML::EID_TAGS:
case EBML::EID_CUES:
{
uint32_t sID = E.getID();
std::cout << "Encountered " << sID << std::endl;
if (seekChecks.count(sID)){
std::cout << "[OFFSET INFORMATION] Segment " << EBML::Element::getIDString(sID) << " is at " << prePos << ", expected was " << seekChecks[sID] << std::endl;
}
}
break;
}
if (depthStash.size()){
depthStash.front() -= E.getOuterLen();
}
@ -36,6 +72,25 @@ bool AnalyserEBML::parsePacket(){
}
while (depthStash.size() && !depthStash.front()){
depthStash.pop_front();
if (lastSeekId){
if (lastSeekId > 0xFFFFFF){
lastSeekId &= 0xFFFFFFF;
}else{
if (lastSeekId > 0xFFFF){
lastSeekId &= 0x1FFFFF;
}else{
if (lastSeekId > 0xFF){
lastSeekId &= 0x3FFF;
}else{
lastSeekId &= 0x7F;
}
}
}
seekChecks[lastSeekId] = segmentOffset+lastSeekPos;
std::cout << "[OFFSET INFORMATION] Segment offset for " << EBML::Element::getIDString(lastSeekId) << " (" << lastSeekId << ") is " << (segmentOffset+lastSeekPos) << std::endl;
lastSeekId = 0;
lastSeekPos = 0;
}
}
///\TODO update mediaTime with the current timestamp
dataBuffer.erase(0, E.getOuterLen());

View file

@ -12,6 +12,10 @@ private:
std::string dataBuffer;
uint64_t curPos;
uint64_t prePos;
uint64_t segmentOffset;
uint32_t lastSeekId;
uint64_t lastSeekPos;
std::map<uint32_t, uint64_t> seekChecks;
std::deque<uint64_t> depthStash;///<Contains bytes to read to go up a level in the element depth.
};