Skip to content

Commit

Permalink
Update videostreamsdata.cpp
Browse files Browse the repository at this point in the history
Honour CPU cap in settings + minor
  • Loading branch information
rodlie committed Mar 22, 2024
1 parent 5404439 commit 4a3d1a9
Showing 1 changed file with 51 additions and 26 deletions.
77 changes: 51 additions & 26 deletions src/core/FileCacheHandlers/videostreamsdata.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
// Fork of enve - Copyright (C) 2016-2020 Maurycy Liebner

#include "videostreamsdata.h"
#include "Private/esettings.h"

stdsptr<VideoStreamsData> VideoStreamsData::sOpen(const QString &path) {
const auto result = std::shared_ptr<VideoStreamsData>(
Expand Down Expand Up @@ -71,14 +72,22 @@ void VideoStreamsData::open() {
}
}

void VideoStreamsData::open(const char * const path) {
void VideoStreamsData::open(const char * const path)
{
fFormatContext = avformat_alloc_context();
if(!fFormatContext) RuntimeThrow("Error allocating AVFormatContext");
if(avformat_open_input(&fFormatContext, path, nullptr, nullptr) != 0) {
RuntimeThrow("Could not open file");
if (!fFormatContext) {
RuntimeThrow(QObject::tr("Error allocating AVFormatContext"));
}
if(avformat_find_stream_info(fFormatContext, nullptr) < 0) {
RuntimeThrow("Could not retrieve stream info");

if (avformat_open_input(&fFormatContext,
path,
nullptr,
nullptr) != 0) {
RuntimeThrow(QObject::tr("Could not open file"));
}
if (avformat_find_stream_info(fFormatContext,
nullptr) < 0) {
RuntimeThrow(QObject::tr("Could not retrieve stream info"));
}

// Find the index of the first audio stream
Expand All @@ -87,45 +96,57 @@ void VideoStreamsData::open(const char * const path) {
const AVCodec *vidCodec = nullptr;
fVideoStream = nullptr;
bool hasAudio = false;
for(uint i = 0; i < fFormatContext->nb_streams; i++) {
for (uint i = 0; i < fFormatContext->nb_streams; i++) {
const AVStream * const iStream = fFormatContext->streams[i];
const AVCodecParameters * const iCodecPars = iStream->codecpar;
const AVMediaType &iMediaType = iCodecPars->codec_type;
if(iMediaType == AVMEDIA_TYPE_VIDEO) {
if (iMediaType == AVMEDIA_TYPE_VIDEO) {
fVideoStreamIndex = static_cast<int>(i);
vidCodecPars = iCodecPars;
vidCodec = avcodec_find_decoder(vidCodecPars->codec_id);
fVideoStream = fFormatContext->streams[fVideoStreamIndex];
fTimeBaseDen = fVideoStream->r_frame_rate.den; //avg_frame_rate ??
fTimeBaseNum = fVideoStream->r_frame_rate.num; //avg_frame_rate ??
if(fTimeBaseDen == 0)
RuntimeThrow("Invalid video frame rate denominator (0)");
if (fTimeBaseDen == 0) {
RuntimeThrow(QObject::tr("Invalid video frame rate denominator (0)"));
}
fFps = static_cast<qreal>(fTimeBaseNum)/fTimeBaseDen;
if(fVideoStream->nb_frames > 0) {
if (fVideoStream->nb_frames > 0) {
fFrameCount = static_cast<int>(fVideoStream->nb_frames);
} else {
const int64_t duration = fFormatContext->duration +
(fFormatContext->duration <= INT64_MAX - 5000 ? 5000 : 0);
fFrameCount = qFloor(duration*fFps/AV_TIME_BASE);
}
break;
} else if(iMediaType == AVMEDIA_TYPE_AUDIO) hasAudio = true;
} else if (iMediaType == AVMEDIA_TYPE_AUDIO) { hasAudio = true; }
}
if (fVideoStreamIndex == -1) {
RuntimeThrow(QObject::tr("Could not retrieve video stream"));
}
if (!vidCodec) {
RuntimeThrow(QObject::tr("Unsupported codec"));
}
if(fVideoStreamIndex == -1)
RuntimeThrow("Could not retrieve video stream");
if(!vidCodec) RuntimeThrow("Unsupported codec");

fCodecContext = avcodec_alloc_context3(vidCodec);
if(!fCodecContext) RuntimeThrow("Error allocating AVCodecContext");
int maxThreads = QThread::idealThreadCount() - 1;
// we set max threads to 16, beyond that ffmpeg will complain and there might be issues
fCodecContext->thread_count = maxThreads > 16 ? 16 : maxThreads;
if(avcodec_parameters_to_context(fCodecContext, vidCodecPars) < 0) {
RuntimeThrow("Failed to copy codec params to codec context");
if (!fCodecContext) {
RuntimeThrow(QObject::tr("Error allocating AVCodecContext"));
}

if(avcodec_open2(fCodecContext, vidCodec, nullptr) < 0) {
RuntimeThrow("Failed to open codec");
int maxThreads = eSettings::sCpuThreadsCapped() - 1;
if (maxThreads > 0) {
fCodecContext->thread_count = maxThreads > 16 ? 16 : maxThreads;
}

if (avcodec_parameters_to_context(fCodecContext,
vidCodecPars) < 0) {
RuntimeThrow(QObject::tr("Failed to copy codec params to codec context"));
}

if (avcodec_open2(fCodecContext,
vidCodec,
nullptr) < 0) {
RuntimeThrow(QObject::tr("Failed to open codec"));
}
fSwsContext = sws_getContext(fCodecContext->width,
fCodecContext->height,
Expand All @@ -136,11 +157,15 @@ void VideoStreamsData::open(const char * const path) {
nullptr, nullptr, nullptr);

fPacket = av_packet_alloc();
if(!fPacket) RuntimeThrow("Error allocating AVPacket");
if (!fPacket) {
RuntimeThrow(QObject::tr("Error allocating AVPacket"));
}
fDecodedFrame = av_frame_alloc();
if(!fDecodedFrame) RuntimeThrow("Error allocating AVFrame");
if (!fDecodedFrame) {
RuntimeThrow(QObject::tr("Error allocating AVFrame"));
}

fOpened = true;

if(hasAudio) fAudioData = AudioStreamsData::sOpen(fPath);
if (hasAudio) { fAudioData = AudioStreamsData::sOpen(fPath); }
}

0 comments on commit 4a3d1a9

Please sign in to comment.