/// <summary>Initializes the FLAC stream decoder</summary> /// <param name="stream">Stream that will be decoded</param> public void InitStream(FlacStream stream) { // Explanation for the GCHandle stuff: The only reference to the FlacStream instance // will very likely remain in unmanaged code. Since the garbage collector cannot // see this reference, given no other references to it exist, the FlacStream instance // would then become a candidate for garbage collection. The GCHandle avoids this. // It will ensure the FlacStream instance is kept alive until it the FLAC stream decoder // is destroyed (at which point we are responsible for invoking its Free() method) GCHandle streamHandle = GCHandle.Alloc(stream, GCHandleType.Normal); try { int result = UnsafeNativeMethods.FLAC__stream_decoder_init_stream( this.decoderHandle, stream.ReadCallbackDelegate, stream.SeekCallbackDelegate, stream.TellCallbackDelegate, stream.LengthCallbackDelegate, stream.EofCallbackDelegate, stream.WriteCallbackDelegate, stream.MetadataCallbackDelegate, stream.ErrorCallbackDelegate, GCHandle.ToIntPtr(streamHandle) ); int goodResult = (int)UnsafeNativeMethods.FLAC__StreamDecoderInitStatus. FLAC__STREAM_DECODER_INIT_STATUS_OK; if (result != goodResult) { // TODO: Transform the error code into an appropriate exception throw new Exception("FLAC__stream_decoder_init_stream() has failed"); } } catch (Exception) { streamHandle.Free(); throw; } }
/// <summary>Initializes the FLAC stream decoder</summary> /// <param name="stream">Stream that will be decoded</param> public void InitStream(FlacStream stream) { // Explanation for the GCHandle stuff: The only reference to the FlacStream instance // will very likely remain in unmanaged code. Since the garbage collector cannot // see this reference, given no other references to it exist, the FlacStream instance // would then become a candidate for garbage collection. The GCHandle avoids this. // It will ensure the FlacStream instance is kept alive until it the FLAC stream decoder // is destroyed (at which point we are responsible for invoking its Free() method) GCHandle streamHandle = GCHandle.Alloc(stream, GCHandleType.Normal); try { int result = UnsafeNativeMethods.FLAC__stream_decoder_init_stream( this.decoderHandle, stream.ReadCallbackDelegate, stream.SeekCallbackDelegate, stream.TellCallbackDelegate, stream.LengthCallbackDelegate, stream.EofCallbackDelegate, stream.WriteCallbackDelegate, stream.MetadataCallbackDelegate, stream.ErrorCallbackDelegate, GCHandle.ToIntPtr(streamHandle) ); int goodResult = (int)UnsafeNativeMethods.FLAC__StreamDecoderInitStatus. FLAC__STREAM_DECODER_INIT_STATUS_OK; if(result != goodResult) { // TODO: Transform the error code into an appropriate exception throw new Exception("FLAC__stream_decoder_init_stream() has failed"); } } catch(Exception) { streamHandle.Free(); throw; } }