private void TranscodeWorker() { while (true) { MediaSample sample = null; lock (sync) { if (samples.Count > 0) { sample = samples.Dequeue(); } } if (sample != null) { if (!transcoder.Push(0, sample)) { var error = transcoder.Error.Clone() as ErrorInfo; LogError("Transcoder.Push", error); transcoder.Close(); transcoder.Dispose(); Dispatcher.BeginInvoke(new Action <ErrorInfo>(SingalEncodeError), error); return; } } else { if (stopEncodeThread) { transcoder.Flush(); transcoder.Close(); transcoder.Dispose(); return; } else { Thread.Sleep(1); } } } }
public int SampleCB(double SampleTime, IMediaSample pSample) { if (!bProcess) { lastSampleTime = SampleTime; return(WinAPI.E_FAIL); } // internal stats ++sampleIndex; long tStart, tEnd; pSample.GetMediaTime(out tStart, out tEnd); Debug.Assert(tStart < tEnd); Debug.Assert(tStart > lastMediaTime); sampleProcessed += tEnd - tStart; sampleDropped += tStart - lastMediaTime - 1; lastMediaTime = tEnd - 1; int dataLen = pSample.GetActualDataLength(); IntPtr bufPtr; int hr = pSample.GetPointer(out bufPtr); Debug.Assert(0 == hr); // BEGIN TRACE int bufSize = pSample.GetSize(); long timeStart, timeEnd; pSample.GetTime(out timeStart, out timeEnd); string msg = string.Format( "SampleCB ({0}) {1}, sampleTime:{2} datalen:{3} bufsize:{4} mediaTime:{5}-{6} time:{7}-{8}", name, sampleIndex, SampleTime, dataLen, bufSize, tStart, tEnd, timeStart, timeEnd); Trace.WriteLine(msg); if (tStart - lastMediaTime - 1 > 0) { msg = string.Format("!!! Frame drop: {0}", tStart - lastMediaTime - 1 > 0); Trace.WriteLine(msg); } //END TRACE byte[] buf = new byte[dataLen]; Marshal.Copy(bufPtr, buf, 0, dataLen); if (file != null) { file.Write(buf, 0, dataLen); } //DBG - simulate encoding error //if (sampleIndex > 100) // goto STOP_CAPTURE; if (mediaState != null && mediaState.mpeg2Enc != null) { PrimoSoftware.AVBlocks.Transcoder enc = mediaState.mpeg2Enc; MediaSample inputSample = new MediaSample(); inputSample.Buffer = new MediaBuffer(buf); inputSample.StartTime = Math.Max(SampleTime, 0); //TODO: end time try { bool pushed = false; // transcoder.Push() is not threads safe. // lock (enc){ } ensure that only one thread is calling transcoder.Push() lock (enc) { pushed = enc.Push(StreamNumber, inputSample); } if (pushed) { return(0); } } catch (Exception ex) { System.Diagnostics.Trace.WriteLine(ex.ToString()); } Trace.WriteLine("PushSample FAILED"); } //STOP_CAPTURE: Trace.WriteLine("SampleCB: Before Post STOP_CAPTURE"); WinAPI.PostMessage(MainWindow, Util.WM_STOP_CAPTURE, new IntPtr(streamNumber), IntPtr.Zero); Trace.WriteLine("SampleCB: After Post STOP_CAPTURE"); bProcess = false; return(WinAPI.E_FAIL); } // end of SampleCB