From 3c3c87c01fdac5a444e72a271dcce60bfebf62b0 Mon Sep 17 00:00:00 2001 From: Mark Heath Date: Wed, 29 Jun 2022 15:38:44 +0100 Subject: [PATCH] avoid spurious argument null exceptions in situation where we fail to encode --- NAudio.Wasapi/MediaFoundationEncoder.cs | 59 ++++++++++++------- NAudio.sln | 10 ++-- .../MediaFoundationEncodeViewModel.cs | 12 +++- 3 files changed, 52 insertions(+), 29 deletions(-) diff --git a/NAudio.Wasapi/MediaFoundationEncoder.cs b/NAudio.Wasapi/MediaFoundationEncoder.cs index 04fd174..bdb4462 100644 --- a/NAudio.Wasapi/MediaFoundationEncoder.cs +++ b/NAudio.Wasapi/MediaFoundationEncoder.cs @@ -57,13 +57,11 @@ namespace NAudio.Wave throw; } } - int count; - availableTypes.GetElementCount(out count); + availableTypes.GetElementCount(out int count); var mediaTypes = new List(count); for (int n = 0; n < count; n++) { - object mediaTypeObject; - availableTypes.GetElement(n, out mediaTypeObject); + availableTypes.GetElement(n, out object mediaTypeObject); var mediaType = (IMFMediaType)mediaTypeObject; mediaTypes.Add(new MediaType(mediaType)); } @@ -222,8 +220,7 @@ namespace NAudio.Wave var writer = CreateSinkWriter(outputFile); try { - int streamIndex; - writer.AddStream(outputMediaType.MediaFoundationObject, out streamIndex); + writer.AddStream(outputMediaType.MediaFoundationObject, out int streamIndex); // n.b. can get 0xC00D36B4 - MF_E_INVALIDMEDIATYPE here writer.SetInputMediaType(streamIndex, inputMediaType.MediaFoundationObject, null); @@ -232,8 +229,14 @@ namespace NAudio.Wave } finally { - Marshal.ReleaseComObject(writer); - Marshal.ReleaseComObject(inputMediaType.MediaFoundationObject); + if (writer != null) + { + Marshal.ReleaseComObject(writer); + } + if (inputMediaType.MediaFoundationObject != null) + { + Marshal.ReleaseComObject(inputMediaType.MediaFoundationObject); + } } } @@ -243,24 +246,35 @@ namespace NAudio.Wave /// Output stream /// Input provider (should be PCM, some encoders will also allow IEEE float) /// One of - public void Encode(Stream outputStream, IWaveProvider inputProvider, Guid transcodeContainerType) { - if (inputProvider.WaveFormat.Encoding != WaveFormatEncoding.Pcm && inputProvider.WaveFormat.Encoding != WaveFormatEncoding.IeeeFloat) { + public void Encode(Stream outputStream, IWaveProvider inputProvider, Guid transcodeContainerType) + { + if (inputProvider.WaveFormat.Encoding != WaveFormatEncoding.Pcm && inputProvider.WaveFormat.Encoding != WaveFormatEncoding.IeeeFloat) + { throw new ArgumentException("Encode input format must be PCM or IEEE float"); } var inputMediaType = new MediaType(inputProvider.WaveFormat); var writer = CreateSinkWriter(new ComStream(outputStream), transcodeContainerType); - try { + try + { writer.AddStream(outputMediaType.MediaFoundationObject, out int streamIndex); // n.b. can get 0xC00D36B4 - MF_E_INVALIDMEDIATYPE here writer.SetInputMediaType(streamIndex, inputMediaType.MediaFoundationObject, null); PerformEncode(writer, streamIndex, inputProvider); - } finally { - Marshal.ReleaseComObject(writer); - Marshal.ReleaseComObject(inputMediaType.MediaFoundationObject); + } + finally + { + if (writer != null) + { + Marshal.ReleaseComObject(writer); + } + if (inputMediaType.MediaFoundationObject != null) + { + Marshal.ReleaseComObject(inputMediaType.MediaFoundationObject); + } } } @@ -292,7 +306,8 @@ namespace NAudio.Wave return writer; } - private static IMFSinkWriter CreateSinkWriter(IStream outputStream, Guid TranscodeContainerType) { + private static IMFSinkWriter CreateSinkWriter(IStream outputStream, Guid TranscodeContainerType) + { // n.b. could try specifying the container type using attributes, but I think // it does a decent job of working it out from the file extension // n.b. AAC encode on Win 8 can have AAC extension, but use MP4 in win 7 @@ -300,10 +315,13 @@ namespace NAudio.Wave IMFSinkWriter writer; var attributes = MediaFoundationApi.CreateAttributes(1); attributes.SetGUID(MediaFoundationAttributes.MF_TRANSCODE_CONTAINERTYPE, TranscodeContainerType); - try { + try + { MediaFoundationInterop.MFCreateMFByteStreamOnStream(outputStream, out var ppByteStream); MediaFoundationInterop.MFCreateSinkWriterFromURL(null, ppByteStream, attributes, out writer); - } finally { + } + finally + { Marshal.ReleaseComObject(attributes); } return writer; @@ -336,16 +354,13 @@ namespace NAudio.Wave private long ConvertOneBuffer(IMFSinkWriter writer, int streamIndex, IWaveProvider inputProvider, long position, byte[] managedBuffer) { long durationConverted = 0; - int maxLength; IMFMediaBuffer buffer = MediaFoundationApi.CreateMemoryBuffer(managedBuffer.Length); - buffer.GetMaxLength(out maxLength); + buffer.GetMaxLength(out var maxLength); IMFSample sample = MediaFoundationApi.CreateSample(); sample.AddBuffer(buffer); - IntPtr ptr; - int currentLength; - buffer.Lock(out ptr, out maxLength, out currentLength); + buffer.Lock(out var ptr, out maxLength, out int currentLength); int read = inputProvider.Read(managedBuffer, 0, maxLength); if (read > 0) { diff --git a/NAudio.sln b/NAudio.sln index 40f3dd3..1cf38df 100644 --- a/NAudio.sln +++ b/NAudio.sln @@ -1,19 +1,19 @@  Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio Version 16 -VisualStudioVersion = 16.0.30717.126 +# Visual Studio Version 17 +VisualStudioVersion = 17.2.32602.215 MinimumVisualStudioVersion = 10.0.40219.1 Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "NAudio", "NAudio\NAudio.csproj", "{DA4F02E3-0B5E-42CD-B8D9-5583FA51D66E}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MidiFileConverter", "MidiFileConverter\MidiFileConverter.csproj", "{5B5897BD-A423-4AF8-8A59-1C1372ED77DB}" +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "MidiFileConverter", "MidiFileConverter\MidiFileConverter.csproj", "{5B5897BD-A423-4AF8-8A59-1C1372ED77DB}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MixDiff", "MixDiff\MixDiff.csproj", "{1293DD10-378A-4370-AEE2-AA1E9E87039B}" +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "MixDiff", "MixDiff\MixDiff.csproj", "{1293DD10-378A-4370-AEE2-AA1E9E87039B}" EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "NAudioTests", "NAudioTests\NAudioTests.csproj", "{5080281A-F9A1-403F-85C7-0DFF6839B07B}" EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "NAudioDemo", "NAudioDemo\NAudioDemo.csproj", "{C37A547B-F31E-45FB-870A-CFA704D06152}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AudioFileInspector", "AudioFileInspector\AudioFileInspector.csproj", "{D29C1659-635C-497B-847E-FE9A5A69ED03}" +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "AudioFileInspector", "AudioFileInspector\AudioFileInspector.csproj", "{D29C1659-635C-497B-847E-FE9A5A69ED03}" EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "NAudioWpfDemo", "NAudioWpfDemo\NAudioWpfDemo.csproj", "{A7B74F85-D353-4ED4-A321-E6E4AD4D7D32}" EndProject diff --git a/NAudioWpfDemo/MediaFoundationEncode/MediaFoundationEncodeViewModel.cs b/NAudioWpfDemo/MediaFoundationEncode/MediaFoundationEncodeViewModel.cs index 7449956..0f45f9e 100644 --- a/NAudioWpfDemo/MediaFoundationEncode/MediaFoundationEncodeViewModel.cs +++ b/NAudioWpfDemo/MediaFoundationEncode/MediaFoundationEncodeViewModel.cs @@ -175,7 +175,7 @@ namespace NAudioWpfDemo.MediaFoundationEncode private void Encode() { - if (String.IsNullOrEmpty(InputFile)||!File.Exists(InputFile)) + if (String.IsNullOrEmpty(InputFile) || !File.Exists(InputFile)) { MessageBox.Show("Please select a valid input file to convert"); return; @@ -192,7 +192,15 @@ namespace NAudioWpfDemo.MediaFoundationEncode if (outputUrl == null) return; using (var encoder = new MediaFoundationEncoder(SelectedMediaType.MediaType)) { - encoder.Encode(outputUrl, reader); + try + { + + encoder.Encode(outputUrl, reader); + } + catch (Exception e) + { + MessageBox.Show(e.Message, "Failed to encode"); + } } } }