diff --git a/Ryujinx.Common/Logging/LogClass.cs b/Ryujinx.Common/Logging/LogClass.cs index 1597805c8..28b344cd3 100644 --- a/Ryujinx.Common/Logging/LogClass.cs +++ b/Ryujinx.Common/Logging/LogClass.cs @@ -9,6 +9,7 @@ namespace Ryujinx.Common.Logging Cpu, Font, Emulation, + FFmpeg, Gpu, Hid, Host1x, diff --git a/Ryujinx.Graphics.Nvdec.H264/FFmpegContext.cs b/Ryujinx.Graphics.Nvdec.H264/FFmpegContext.cs index 98754c767..c402c574b 100644 --- a/Ryujinx.Graphics.Nvdec.H264/FFmpegContext.cs +++ b/Ryujinx.Graphics.Nvdec.H264/FFmpegContext.cs @@ -1,16 +1,25 @@ using FFmpeg.AutoGen; +using Ryujinx.Common.Logging; using System; +using System.Runtime.InteropServices; namespace Ryujinx.Graphics.Nvdec.H264 { unsafe class FFmpegContext : IDisposable { + private readonly av_log_set_callback_callback _logFunc; private readonly AVCodec* _codec; private AVPacket* _packet; private AVCodecContext* _context; public FFmpegContext() { + _logFunc = Log; + + // Redirect log output + ffmpeg.av_log_set_level(ffmpeg.AV_LOG_MAX_OFFSET); + ffmpeg.av_log_set_callback(_logFunc); + _codec = ffmpeg.avcodec_find_decoder(AVCodecID.AV_CODEC_ID_H264); _context = ffmpeg.avcodec_alloc_context3(_codec); @@ -19,6 +28,42 @@ namespace Ryujinx.Graphics.Nvdec.H264 _packet = ffmpeg.av_packet_alloc(); } + private void Log(void* p0, int level, string format, byte* vl) + { + if (level > ffmpeg.av_log_get_level()) + { + return; + } + + int lineSize = 1024; + byte* lineBuffer = stackalloc byte[lineSize]; + int printPrefix = 1; + + ffmpeg.av_log_format_line(p0, level, format, vl, lineBuffer, lineSize, &printPrefix); + + string line = Marshal.PtrToStringAnsi((IntPtr)lineBuffer).Trim(); + + switch (level) + { + case ffmpeg.AV_LOG_PANIC: + case ffmpeg.AV_LOG_FATAL: + case ffmpeg.AV_LOG_ERROR: + Logger.Error?.Print(LogClass.FFmpeg, line); + break; + case ffmpeg.AV_LOG_WARNING: + Logger.Warning?.Print(LogClass.FFmpeg, line); + break; + case ffmpeg.AV_LOG_INFO: + Logger.Info?.Print(LogClass.FFmpeg, line); + break; + case ffmpeg.AV_LOG_VERBOSE: + case ffmpeg.AV_LOG_DEBUG: + case ffmpeg.AV_LOG_TRACE: + Logger.Debug?.Print(LogClass.FFmpeg, line); + break; + } + } + public int DecodeFrame(Surface output, ReadOnlySpan bitstream) { // Ensure the packet is clean before proceeding