coda vpu: decode without read for eof packets. clean up

This commit is contained in:
wang-bin
2015-10-27 19:38:17 +08:00
parent 1c98a2c15d
commit b03abbfdbe
5 changed files with 51 additions and 96 deletions
+1 -2
View File
@@ -9,7 +9,6 @@ void dma_copy_from_vmem(unsigned char* dst, unsigned int src, int len);
}
namespace QtAV {
namespace vpu {
InteropResource::InteropResource()
: scaler(0)
{}
@@ -48,7 +47,7 @@ bool InteropResource::map(const FBSurfacePtr &surface, VideoFrame *img, int)
// qMin(scaler->outHeight(), img->height)
dma_copy_from_vmem(img->bits(0), (unsigned int)(quintptr)scaler->outPlanes().at(0), img->bytesPerLine(0)*img->height());
} else {
qWarning("different gpu/host_mem stride");
qWarning("different stride. vmem: %d, host: %d", img->bytesPerLine(0), scaler->outLineSizes().at(0));
for (int i = 0; i < img->height(); ++i)
dma_copy_from_vmem(img->bits(0) + i*img->bytesPerLine(0), (unsigned int)(quintptr)scaler->outPlanes().at(0) + i*scaler->outLineSizes().at(0), img->bytesPerLine(0));
}
+2 -3
View File
@@ -32,7 +32,7 @@ public:
/*!
* \brief map
* \param surface vpu decoded surface
* \param info [width, height, linesize]
* \param img contains the target frame information
* \param w frame width(visual width) without alignment, <= vpu surface width
* \param h frame height(visual height)
* \param plane useless now
@@ -55,11 +55,10 @@ public:
* \param frame_h frame height(visual height)
*/
void setSurface(const FBSurfacePtr& surface, int frame_w, int frame_h);
/// GLTextureSurface only supports rgb32
void* map(SurfaceType type, const VideoFormat& fmt, void* handle, int plane) Q_DECL_OVERRIDE;
void unmap(void *) Q_DECL_OVERRIDE {}
protected:
/// copy from gpu (optimized if possible) and convert to target format if necessary
/// copy from gpu (optimized if possible) and convert to target format + scaled to target size if necessary
void* mapToHost(const VideoFormat &format, void *handle, int plane);
private:
InteropResourcePtr m_resource;
+48 -89
View File
@@ -1,23 +1,4 @@
/******************************************************************************
QtAV: Media play library based on Qt and FFmpeg
Copyright (C) 2013-2015 Wang Bin <wbsecg1@gmail.com>
Miroslav Bendik <miroslav.bendik@gmail.com>
* This file is part of QtAV
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 2.1 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
******************************************************************************/
#include "QtAV/VideoDecoder.h"
@@ -94,9 +75,10 @@ class VideoDecoderVPUPrivate Q_DECL_FINAL: public VideoDecoderPrivate
public:
VideoDecoderVPUPrivate()
: VideoDecoderPrivate()
, instIdx(0), coreIdx(0)
, coreIdx(0)
, tiled2LinearEnable(false) //?
, mapType(LINEAR_FRAME_MAP) //?
, instIdx(0)
, chunkReuseRequired(false)
, seqInited(false), seqFilled(false)
, bsfillSize(0)
@@ -125,11 +107,12 @@ public:
bool initSeq();
bool processHeaders(int* seqHeaderSize, int* picHeaderSize, const Packet& pkt, int fps_num, int fps_den, int nb_index_entries);
// user config
int instIdx, coreIdx; //0
int coreIdx; // MAX_NUM_VPU_CORE = 1
bool useRot, useDering; //false
bool tiled2LinearEnable;
TiledMapType mapType;
// vpu status
int instIdx;
bool chunkReuseRequired; //false
bool seqInited, seqFilled; //false
int bsfillSize; //0
@@ -420,9 +403,6 @@ bool VideoDecoderVPUPrivate::open()
bsfillSize = 0;
chunkReuseRequired = false;
frameIdx = 0;
width = codec_ctx->width;
height = codec_ctx->height;
qDebug("open ok. size: %dx%d", width, height);
interop_res = vpu::InteropResourcePtr(new vpu::InteropResource());
return true;
}
@@ -530,30 +510,14 @@ qDebug("initSeq: %d", seqInited);
framebufHeight = FFALIGN(scaledHeight, 32); // framebufheight must be aligned by 31 because of the number of MB height would be odd in each filed picture.
else
framebufHeight = FFALIGN(scaledHeight, 16);
#ifdef SUPPORT_USE_VPU_ROTATOR
rotbufWidth = (decConfig.rotAngle == 90 || decConfig.rotAngle == 270) ?
FFALIGN(scaledHeight, 16) : FFALIGN(scaledWidth, 16);
rotbufHeight = (decConfig.rotAngle == 90 || decConfig.rotAngle == 270) ?
FFALIGN(scaledWidth, 16) : FFALIGN(scaledHeight, 16);
#endif
} else {
framebufWidth = FFALIGN(initialInfo.picWidth, 16);
// TODO: vpurun decConfig.maxHeight
// TODO: omx fbHeight align 16
if (IsSupportInterlaceMode(decOP.bitstreamFormat, &initialInfo))
framebufHeight = FFALIGN(initialInfo.picHeight, 32); // framebufheight must be aligned by 31 because of the number of MB height would be odd in each filed picture.
else
framebufHeight = FFALIGN(initialInfo.picHeight, 16);
#ifdef SUPPORT_USE_VPU_ROTATOR
rotbufWidth = (decConfig.rotAngle == 90 || decConfig.rotAngle == 270) ?
FFALIGN(initialInfo.picHeight, 16) : FFALIGN(initialInfo.picWidth, 16);
rotbufHeight = (decConfig.rotAngle == 90 || decConfig.rotAngle == 270) ?
FFALIGN(initialInfo.picWidth, 16) : FFALIGN(initialInfo.picHeight, 16);
#endif
}
#ifdef SUPPORT_USE_VPU_ROTATOR
rotStride = rotbufWidth;
#endif
framebufStride = framebufWidth;
framebufFormat = FORMAT_420;
// vpurun: allocate out buffer of size framebufSize for rendering. we do not need it
@@ -642,59 +606,57 @@ bool VideoDecoderVPU::decode(const Packet &packet)
qWarning("decode finished");
return false;
}
if (packet.data.isEmpty())
return true;
if (packet.isEOF()) { //decode the trailing frames
QByteArray chunkData(packet.data);
DecOpenParam &decOP = d.decOP;
int seqHeaderSize = 0; //also used in FLUSH_BUFFER
int picHeaderSize = 0;
if (packet.isEOF()) {
if (!d.flush()) {
qDebug("Error decode EOS"); // when?
return false;
}
chunkData = QByteArray(); //decode the trailing frames
qDebug("eof packet");
//goto FLUSH_BUFFER; //TODO: decode trailing frames
}
QByteArray chunkData(packet.data);
DecOpenParam &decOP = d.decOP;
if (decOP.bitstreamMode == BS_MODE_PIC_END) { //TODO: no check in omx. it's always true here
} else {
if (decOP.bitstreamMode == BS_MODE_PIC_END) { //TODO: no check in omx. it's always true here
if (!d.chunkReuseRequired) {
qDebug("!chunkReuseRequired VPU_DecSetRdPtr");
VPU_DecSetRdPtr(d.handle, decOP.bitstreamBuffer, 1);
}
}
if (!d.chunkReuseRequired) {
qDebug("!chunkReuseRequired VPU_DecSetRdPtr");
VPU_DecSetRdPtr(d.handle, decOP.bitstreamBuffer, 1);
if (!d.processHeaders(&seqHeaderSize, &picHeaderSize, packet, property("fps_num").toInt(), property("fps_den").toInt(), property("nb_index_entries").toInt())) {
qWarning("procesHeader error");
return false;
}
}
// Fill VCL data
switch(decOP.bitstreamFormat) {
case STD_VP3:
case STD_THO:
//const int size = WriteBsBufFromBufHelper(coreIdx, handle, &vbStream, picHeader, picHeaderSize, decOP.streamEndian);
break;
default: {
if (decOP.bitstreamFormat == STD_RV) {
const int cSlice = chunkData.at(0) + 1;
chunkData.remove(0, 1+(cSlice*8));
}
const int size = WriteBsBufFromBufHelper(d.coreIdx, d.handle, &d.vbStream, (BYTE*)chunkData.constData(), chunkData.size(), decOP.streamEndian);
if (size <0) {
qWarning("WriteBsBufFromBufHelper failed Error code is 0x%x", size);
return false;
}
d.bsfillSize += size;
}
}
int seqHeaderSize = 0; //also used in FLUSH_BUFFER
int picHeaderSize = 0;
if (!d.chunkReuseRequired) {
if (!d.processHeaders(&seqHeaderSize, &picHeaderSize, packet, property("fps_num").toInt(), property("fps_den").toInt(), property("nb_index_entries").toInt())) {
qWarning("procesHeader error");
return false;
}
}
// Fill VCL data
switch(decOP.bitstreamFormat) {
case STD_VP3:
case STD_THO:
//const int size = WriteBsBufFromBufHelper(coreIdx, handle, &vbStream, picHeader, picHeaderSize, decOP.streamEndian);
break;
default: {
if (decOP.bitstreamFormat == STD_RV) {
const int cSlice = chunkData.at(0) + 1;
chunkData.remove(0, 1+(cSlice*8));
}
const int size = WriteBsBufFromBufHelper(d.coreIdx, d.handle, &d.vbStream, (BYTE*)chunkData.constData(), chunkData.size(), decOP.streamEndian);
if (size <0) {
qWarning("WriteBsBufFromBufHelper failed Error code is 0x%x", size);
qDebug("bsfillSize: %d", d.bsfillSize);
//chunkIdx++;
if (!d.initSeq())
return false;
}
d.bsfillSize += size;
d.chunkReuseRequired = false;
}
break;
}
qDebug("bsfillSize: %d", d.bsfillSize);
//chunkIdx++;
if (!d.initSeq())
return false;
d.chunkReuseRequired = false;
//FLUSH_BUFFER:
if(!(d.int_reason & (1<<INT_BIT_BIT_BUF_EMPTY)) && !(d.int_reason & (1<<INT_BIT_DEC_FIELD))) {
// ppu here
@@ -801,9 +763,8 @@ qDebug("VPU_ClearInterrupt");
qDebug("decodefinish. indexFrameDisplay==-1");
d.decodefinish = true;
}
if (d.decodefinish) {
if (true)///*!ppuEnable*/ || decodeIdx == 0)
return !packet.isEOF(); // EOS
if (d.decodefinish) { //ppu here
return false;
}
if (d.outputInfo.indexFrameDisplay == -3 ||
d.outputInfo.indexFrameDisplay == -2 ) // BIT doesn't have picture to be displayed, or frame drop
@@ -842,25 +803,23 @@ void VideoDecoderVPU::flush()
{
DPTR_D(VideoDecoderVPU);
VPU_DecFrameBufferFlush(d.handle);
d.display_queue = ring<FBSurfacePtr>(0);
}
VideoFrame VideoDecoderVPU::frame()
{
DPTR_D(VideoDecoderVPU);
// 0 on success
if (d.display_queue.empty()) {
qDebug("VPU has no frame decoded");
return VideoFrame();
}
FBSurfacePtr surf(d.display_queue.front());
d.display_queue.pop_front();
// FIXME: width()/height() 0
// TODO: timestamp is packet pts in OMX!
//qDebug("frame size: %dx%d %dx%d", width(), height(), d.codec_ctx->width, d.codec_ctx->height);
VideoFrame frame(d.codec_ctx->width, d.codec_ctx->height, VideoFormat::Format_RGB32);
//frame.setTimestamp();
vpu::SurfaceInteropGAL *interop = new vpu::SurfaceInteropGAL(d.interop_res);
interop->setSurface(surf, width(), height()); //width() valid?
interop->setSurface(surf, d.codec_ctx->width, d.codec_ctx->height);
frame.setMetaData(QStringLiteral("surface_interop"), QVariant::fromValue(VideoSurfaceInteropPtr(interop)));
return frame;
}
-1
View File
@@ -167,7 +167,6 @@ bool GALScaler::convert(const quint8 * const src[], const int srcStride[])
GC_ENSURE(gco2D_EnableDither(egn2D, gcvFALSE), false)
GC_ENSURE(gco2D_Flush(egn2D), false);
GC_ENSURE(gcoHAL_Commit(d.test2D.runtime.hal, gcvTRUE), false);
return true;
}
-1
View File
@@ -1,7 +1,6 @@
#include <ImageConverter.h>
namespace QtAV {
class GALScalerPrivate;
class GALScaler Q_DECL_FINAL : public ImageConverter
{