Пример #1
0
        /// <summary>
        /// Called on a new thread to process events from the graph.  The thread
        /// exits when the graph finishes.
        /// </summary>
        private void EventWait()
        {
            // Returned when GetEvent is called but there are no events
            const int E_ABORT = unchecked ((int)0x80004004);

            int       hr;
            IntPtr    p1, p2;
            EventCode ec;
            EventCode exitCode = 0;

            IMediaEvent mediaEvent = (IMediaEvent)this.filterGraph;

            do
            {
                // Read the event
                for (hr = mediaEvent.GetEvent(out ec, out p1, out p2, 100);
                     hr >= 0;
                     hr = mediaEvent.GetEvent(out ec, out p1, out p2, 100))
                {
                    switch (ec)
                    {
                    // If the clip is finished playing
                    case EventCode.EndOfSegment:
                    case EventCode.StreamControlStopped:
                    case EventCode.Complete:
                    case EventCode.ErrorAbort:
                    case EventCode.UserAbort:
                        exitCode = ec;

                        // Release any resources the message allocated
                        hr = mediaEvent.FreeEventParams(ec, p1, p2);
                        DsError.ThrowExceptionForHR(hr);
                        break;

                    default:
                        // Release any resources the message allocated
                        hr = mediaEvent.FreeEventParams(ec, p1, p2);
                        DsError.ThrowExceptionForHR(hr);
                        break;
                    }
                }

                // If the error that exited the loop wasn't due to running out of events
                if (hr != E_ABORT)
                {
                    DsError.ThrowExceptionForHR(hr);
                }
            }while (exitCode == 0);

            // Send an event saying we are complete
            if (this.Completed != null)
            {
                var ca = new DESCompletedArgs(exitCode);
                this.Completed(this, ca);
            }

            // Exit the thread
        }
Пример #2
0
        /// <summary>
        /// Called on a new thread to process events from the graph.  The thread
        /// exits when the graph finishes.
        /// </summary>
        private void EventWait()
        {
            // Returned when GetEvent is called but there are no events
            const int E_ABORT = unchecked ((int)0x80004004);

            int       hr;
            IntPtr    p1, p2;
            EventCode ec;
            EventCode exitCode = 0;

            IMediaEvent pEvent = (IMediaEvent)m_FilterGraph;

            do
            {
                // Read the event
                for (
                    hr = pEvent.GetEvent(out ec, out p1, out p2, 100);
                    hr >= 0;
                    hr = pEvent.GetEvent(out ec, out p1, out p2, 100)
                    )
                {
                    Debug.WriteLine(ec);
                    switch (ec)
                    {
                    // If the clip is finished playing
                    case EventCode.Complete:
                    case EventCode.ErrorAbort:
                    case EventCode.UserAbort:
                        exitCode = ec;

                        // Release any resources the message allocated
                        hr = pEvent.FreeEventParams(ec, p1, p2);
                        DsError.ThrowExceptionForHR(hr);
                        break;

                    default:
                        // Release any resources the message allocated
                        hr = pEvent.FreeEventParams(ec, p1, p2);
                        DsError.ThrowExceptionForHR(hr);
                        break;
                    }
                }

                // If the error that exited the loop wasn't due to running out of events
                if (hr != E_ABORT)
                {
                    DsError.ThrowExceptionForHR(hr);
                }
            } while (exitCode == 0);

            // Send an event saying we are complete
            IsCompleted = true;
        } // Exit the thread
Пример #3
0
        public void Run()
        {
            media_control = GraphBuilder as IMediaControl;

            media_event = GraphBuilder as IMediaEvent;

            Console.WriteLine("Started filter graph");
            media_control.Run();

            bool stop = false;

            while (!stop)
            {
                System.Threading.Thread.Sleep(500);
                Console.Write(".");
                EventCode ev;
                IntPtr    p1, p2;
                if (media_event.GetEvent(out ev, out p1, out p2, 0) == 0)
                {
                    if (ev == EventCode.Complete || ev == EventCode.UserAbort)
                    {
                        Console.WriteLine("Done");
                        stop = true;
                        media_control.Stop();
                    }
                    else if (ev == EventCode.ErrorAbort)
                    {
                        Console.WriteLine("An Error occurred: HRESULT={0:X}", p1);
                        media_control.Stop();
                        stop = true;
                    }
                    media_event.FreeEventParams(ev, p1, p2);
                }
            }
        }
Пример #4
0
            /// <summary>
            /// Thread which monitors events and raises them
            /// </summary>
            private void Monitor()
            {
                int eventCode, param1, param2;

                while (true)
                {
                    try
                    {
                        // Check for an event
                        iME.GetEvent(out eventCode, out param1, out param2, -1);

                        // Raise the event if anyone is interested
                        if (FgmEvent != null)
                        {
                            FgmEvent(this, new FgmEventArgs(eventCode, param1, param2));
                        }

                        //ParseEvent(eventCode, param1, param2);
                        iME.FreeEventParams(eventCode, param1, param2);
                    }
                    catch (COMException e) // Timedout waiting for event
                    {
                        Console.WriteLine(e.ToString());
                    }
                }
            }
Пример #5
0
        /// <summary>
        /// Wait for direct show events to happen. This approach uses waiting on an event handle.
        /// The nice thing about doing it this way is that you aren't in the windows message
        /// loop, and don't have to worry about reentrancy or taking too long. Plus, being
        /// in a class as we are, we don't have access to the message loop.
        /// Alternately, you can receive your events as windows messages.  See IMediaEventEx.SetNotifyWindow.</summary>
        private void MediaEventWait()
        {
            // Returned when GetEvent is called but there are no events
            const int E_ABORT = unchecked ((int)0x80004004);

            // Read the events
            for (;;)
            {
                lock (m_shutdown_lock) if (m_shutdown)
                    {
                        break;
                    }                                                         // shutdown the thread when flagged

                IntPtr p1, p2; EventCode ec;
                int    hr = m_media_event.GetEvent(out ec, out p1, out p2, 0);
                if (hr == E_ABORT)
                {
                    m_event.WaitOne(-1, true); continue;
                }                                                                          // Wait for an event
                else if (hr < 0)
                {
                    DsError.ThrowExceptionForHR(hr);                             // If the error wasn't due to running out of events
                }
                //Debug.WriteLine("Video Event: " + ec); // Write the event name to the debug window

                // If the clip is finished playing
                if (ec == EventCode.Complete)
                {
                    Stop();                     // Call Stop() to set state
                }
                // Release any resources the message allocated
                DsError.ThrowExceptionForHR(m_media_event.FreeEventParams(ec, p1, p2));
            }
        }
Пример #6
0
        //TODO maybe we can replace this stuff with BaseDSGraph someday
        private void EventListener()
        {
            Debug.WriteLine("EventListener listening");
            _eventListenerRunning = true;

            IntPtr param1, param2;

            while (_eventListenerRunning)
            {
                int hr;

                EventCode eventCode;
                hr = _mediaEvent.GetEvent(out eventCode, out param1, out param2, 3000);
                if (hr == 0)
                {
                    Debug.WriteLine("EventListener got " + eventCode.ToString());
                    if (eventCode == EventCode.Complete)
                    {
                        Stop();
                        Run();
                    }
                    _mediaEvent.FreeEventParams(eventCode, param1, param2);
                }
            }

            Debug.WriteLine("EventListener exit");
        }
Пример #7
0
    // FIXME this needs some work, to be completely in-tune with needs.
    public void MediaEventLoop(Action <double> UpdateProgress)
    {
        mediaEvent.CancelDefaultHandling(EventCode.StateChange);
        //mediaEvent.CancelDefaultHandling(EventCode.Starvation);
        while (stopMediaEventLoop == false)
        {
            try
            {
                EventCode ev;
                IntPtr    p1, p2;
                if (mediaEvent.GetEvent(out ev, out p1, out p2, 0) == 0)
                {
                    switch (ev)
                    {
                    case EventCode.Complete:
                        Stopping.Fire(this, null);
                        if (UpdateProgress != null)
                        {
                            UpdateProgress(source.PercentageCompleted);
                        }
                        return;

                    case EventCode.StateChange:
                        FilterState state = (FilterState)p1.ToInt32();
                        if (state == FilterState.Stopped || state == FilterState.Paused)
                        {
                            Stopping.Fire(this, null);
                        }
                        else if (state == FilterState.Running)
                        {
                            Starting.Fire(this, null);
                        }
                        break;
                        // FIXME add abort and stuff, and propagate this.
                    }
                    //                        Trace.WriteLine(ev.ToString() + " " + p1.ToInt32());
                    mediaEvent.FreeEventParams(ev, p1, p2);
                }
                else
                {
                    if (UpdateProgress != null)
                    {
                        UpdateProgress(source.PercentageCompleted);
                    }
                    // FiXME use AutoResetEvent
                    Thread.Sleep(100);
                }
            }
            catch (Exception e)
            {
                Trace.WriteLine("MediaEventLoop: " + e);
            }
        }
    }
Пример #8
0
        static void Main(string[] args)
        {
            try
            {
                IGraphBuilder pGraph = (IGraphBuilder) new FilterGraph();
                Console.WriteLine("Building graph...");

                BuildGraph(pGraph, @"bbb_360p_10sec.mp4");
                Console.WriteLine("Running...");

                IMediaControl pMediaControl = (IMediaControl)pGraph;
                IMediaEvent   pMediaEvent   = (IMediaEvent)pGraph;

                int hr = pMediaControl.Run();
                checkHR(hr, "Can't run the graph");

                bool stop = false;
                while (!stop)
                {
                    System.Threading.Thread.Sleep(50);
                    Console.Write(".");
                    EventCode ev;
                    IntPtr    p1, p2;
                    System.Windows.Forms.Application.DoEvents();
                    while (pMediaEvent.GetEvent(out ev, out p1, out p2, 0) == 0)
                    {
                        if (ev == EventCode.Complete || ev == EventCode.UserAbort)
                        {
                            Console.WriteLine("Done!");
                            stop = true;
                        }
                        else if (ev == EventCode.ErrorAbort)
                        {
                            Console.WriteLine("An error occured: HRESULT={0:X}", p1);
                            pMediaControl.Stop();
                            stop = true;
                        }
                        pMediaEvent.FreeEventParams(ev, p1, p2);
                    }
                }
            }
            catch (COMException ex)
            {
                Console.WriteLine("COM error: " + ex.ToString());
            }
            catch (Exception ex)
            {
                Console.WriteLine("Error: " + ex.ToString());
            }
        }
Пример #9
0
            static void Main(string[] args)
            {
                try
                {
                    IGraphBuilder graph = (IGraphBuilder) new FilterGraph();
                    Console.WriteLine("Building graph...");
                    BuildGraph(graph, @"J:\TORRENT\1. Фильмы\Mult.RU.320x240\03 Ежи и Петруччо\01 Когда-то.mp4");
                    Console.WriteLine("Running...");
                    IMediaControl mediaControl = (IMediaControl)graph;
                    IMediaEvent   mediaEvent   = (IMediaEvent)graph;
                    int           hr           = mediaControl.Run();
                    checkHR(hr, "Can't run the graph");
                    bool stop = false;
                    while (!stop)
                    {
                        System.Threading.Thread.Sleep(500);
                        Console.Write(".");
                        EventCode ev;
                        IntPtr    p1, p2;

                        System.Windows.Forms.Application.DoEvents();
                        while (mediaEvent.GetEvent(out ev, out p1, out p2, 0) == 0)
                        {
                            if (ev == EventCode.Complete || ev == EventCode.UserAbort)
                            {
                                Console.WriteLine("Done!");
                                stop = true;
                            }
                            else
                            if (ev == EventCode.ErrorAbort)
                            {
                                Console.WriteLine("An error occured: HRESULT={0:X}", p1);
                                mediaControl.Stop();
                                stop = true;
                            }
                            mediaEvent.FreeEventParams(ev, p1, p2);
                        }
                    }
                }
                catch (COMException ex)
                {
                    Console.WriteLine("COM error: " + ex.ToString());
                }
                catch (Exception ex)
                {
                    Console.WriteLine("Error: " + ex.ToString());
                }
            }
Пример #10
0
        private void TestNotify()
        {
            int       hr;
            IntPtr    p1, p2;
            IntPtr    p3 = IntPtr.Zero, p4 = IntPtr.Zero;
            EventCode ec;
            bool      bPassed = false;
            bool      bDone   = false;

            IMediaEvent pEvent = (IMediaEvent)m_FilterGraph;

            hr = m_mes.Notify(EC_FileComplete, new IntPtr(1), new IntPtr(2));
            DsError.ThrowExceptionForHR(hr);

            ((IMediaControl)m_FilterGraph).Run();

            // Read the event
            for (
                hr = pEvent.GetEvent(out ec, out p1, out p2, 5000);
                hr >= 0 && !bDone;
                hr = pEvent.GetEvent(out ec, out p1, out p2, 5000)
                )
            {
                Debug.WriteLine(ec);

                if (ec == EC_FileComplete)
                {
                    bPassed = true;
                    p3      = p1;
                    p4      = p2;
                }
                else if (ec == EventCode.Complete)
                {
                    break;
                }
                else
                {
                    hr = pEvent.FreeEventParams(ec, p1, p2);
                }
            }

            Debug.Assert(bPassed && p3.ToInt64() == 1 && p4.ToInt64() == 2, "Notify");
        }
Пример #11
0
 public void OnGraphEvent()
 {
     try
     {
         IntPtr    evpar1;
         IntPtr    evpar2;                                                 // = Marshal.AllocHGlobal(4);
         EventCode ev;
         if (mediaEvent.GetEvent(out ev, out evpar1, out evpar2, 10) == 0) //got event
         {
             int ip1 = (int)evpar1;                                        //Marshal.ReadInt32(evpar1);
             int ip2 = (int)evpar2;                                        //Marshal.ReadInt32(evpar2);
             lock (eventlog)
             {
                 eventlog.AddLast(new GraphEvent(ev, ip1, ip2));
             }
             if (ev == EventCode.Complete || ev == EventCode.UserAbort)
             {
                 mediaControl.Stop();
             }
             if (ev == EventCode.ErrorAbort)
             {
                 int hr = ip1;
                 DsError.ThrowExceptionForHR(hr);
             }
             if (ev == EventCode.DeviceLost)
             {
                 Program.mainform.filterz.RefreshCategories();
             }
         }
         mediaEvent.FreeEventParams(ev, evpar1, evpar2);
     }
     catch (COMException ex)
     {
         if (ex.ErrorCode != unchecked ((int)0x80070006)) //E_HANDLE
         {
             ShowCOMException(ex, "An error occured in the graph");
         }
     }
     catch (Exception e)
     {
         MessageBox.Show(e.Message, "Exception caught while getting a graph event");
     }
 }
Пример #12
0
        /// <summary>
        /// Test all methods
        /// </summary>
        public void DoTests()
        {
            int       hr;
            IntPtr    hEvent;
            IntPtr    p1, p2;
            EventCode ec;

            BuildGraph();

            hr = m_mediaEvent.GetEventHandle(out hEvent);
            DsError.ThrowExceptionForHR(hr);

            ManualResetEvent mre = new ManualResetEvent(false);

            mre.SafeWaitHandle = new Microsoft.Win32.SafeHandles.SafeWaitHandle(hEvent, true);

            // Should get an event before this
            bool b = mre.WaitOne(5000, true);

            Debug.Assert(b, "GetEventHandle");

            // I don't know what event I may get, so I don't know how to check it

            hr = m_mediaEvent.GetEvent(out ec, out p1, out p2, 0);
            DsError.ThrowExceptionForHR(hr);

            hr = m_mediaEvent.FreeEventParams(ec, p1, p2);
            DsError.ThrowExceptionForHR(hr);

            hr = m_mediaEvent.CancelDefaultHandling(EventCode.Repaint);
            DsError.ThrowExceptionForHR(hr);

            hr = m_mediaEvent.RestoreDefaultHandling(EventCode.Repaint);
            DsError.ThrowExceptionForHR(hr);

            // The clip is 4 seconds long, so timeout in 5
            hr = m_mediaEvent.WaitForCompletion(5000, out ec);
            DsError.ThrowExceptionForHR(hr);

            // The video should have successfully played
            Debug.Assert(ec == EventCode.Complete, "WaitForCompletion");
        }
Пример #13
0
 private void button1_Click(object sender, EventArgs e)
 {
     try
     {
         IGraphBuilder graph = (IGraphBuilder) new FilterGraph();
         BuildGraph(graph);
         IMediaControl mediaControl = (IMediaControl)graph;
         IMediaEvent   mediaEvent   = (IMediaEvent)graph;
         int           hr           = mediaControl.Run();
         bool          stop         = false;
         while (!stop)
         {
             System.Threading.Thread.Sleep(500);
             EventCode ev;
             IntPtr    p1, p2;
             System.Windows.Forms.Application.DoEvents();
             while (mediaEvent.GetEvent(out ev, out p1, out p2, 0) == 0)
             {
                 if (ev == EventCode.Complete || ev == EventCode.UserAbort)
                 {
                     stop = true;
                 }
                 else
                 if (ev == EventCode.ErrorAbort)
                 {
                     mediaControl.Stop();
                     stop = true;
                 }
                 mediaEvent.FreeEventParams(ev, p1, p2);
             }
         }
     }
     catch (COMException ex)
     {
         MessageBox.Show("COM Error" + ex.ToString());
     }
     catch (Exception ex)
     {
         MessageBox.Show("Error:" + ex.ToString());
     }
 }
Пример #14
0
        public void Run()
        {
            media_control = GraphBuilder as IMediaControl;

            media_event = GraphBuilder as IMediaEvent;

            Console.WriteLine("Started filter graph");
            media_control.Run();

            bool stop = false;

            while (!stop)
            {
                System.Threading.Thread.Sleep(500);
                Console.Write(".");
                EventCode ev;
                IntPtr p1, p2;
                if (media_event.GetEvent(out ev, out p1, out p2, 0) == 0)
                {
                    if (ev == EventCode.Complete || ev == EventCode.UserAbort)
                    {
                        Console.WriteLine("Done");
                        stop = true;
                        media_control.Stop();
                    }
                    else if (ev == EventCode.ErrorAbort)
                    {
                        Console.WriteLine("An Error occurred: HRESULT={0:X}", p1);
                        media_control.Stop();
                        stop = true;
                    }
                    media_event.FreeEventParams(ev, p1, p2);
                }
            }
        }
Пример #15
0
        //void eventListener_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
        //{
        //  this.CloseAudioFile();
        //}

        /// <summary>
        /// Called on a new thread to process events from the graph.  The thread
        /// exits when the graph finishes.  Cancelling is done here.
        /// </summary>
        private void EventWait()
        {
            // Returned when GetEvent is called but there are no events
            const int E_ABORT = unchecked ((int)0x80004004);

            int       hr;
            IntPtr    p1, p2;
            EventCode ec;
            EventCode exitCode = 0;

            IMediaEvent pEvent = (IMediaEvent)this.filterGraph;

            do
            {
                // Read the event
                for (
                    hr = pEvent.GetEvent(out ec, out p1, out p2, 100);
                    hr >= 0 && this.currentState == PlayState.Running;
                    hr = pEvent.GetEvent(out ec, out p1, out p2, 100)
                    )
                {
                    switch (ec)
                    {
                    // If all files finished playing
                    case EventCode.Complete:
                    case EventCode.ErrorAbort:
                    case EventCode.UserAbort:
                        ChangeState(PlayState.Exiting);
                        exitCode = ec;
                        break;
                    }

                    // Release any resources the message allocated
                    hr = pEvent.FreeEventParams(ec, p1, p2);
                    DsError.ThrowExceptionForHR(hr);
                }

                // If the error that exited the loop wasn't due to running out of events
                if (hr != E_ABORT)
                {
                    DsError.ThrowExceptionForHR(hr);
                }
            } while (this.currentState == PlayState.Running);

            // If the user cancelled
            if (this.currentState == PlayState.Cancelling)
            {
                // Stop the graph, send an appropriate exit code
                hr       = this.mediaControl.Stop();
                exitCode = EventCode.UserAbort;
            }


            // Send an event saying we are complete
            if (exitCode == EventCode.Complete && Completed != null)
            {
                CompletedArgs ca = new CompletedArgs(exitCode);
                Completed(this, ca);
            }
            //threadCompleted = true;
        } // Exit the thread
Пример #16
0
        /// <summary>
        /// Called on a new thread to process events from the graph.  The thread
        /// exits when the graph finishes.
        /// </summary>
        private void EventWait()
        {
            // Returned when GetEvent is called but there are no events
            const int E_ABORT = unchecked ((int)0x80004004);

            int       hr;
            IntPtr    p1, p2;
            EventCode ec;
            EventCode exitCode = 0;

            IMediaEvent pEvent = (IMediaEvent)m_FilterGraph;

            do
            {
                // Read the event
                for (
                    hr = pEvent.GetEvent(out ec, out p1, out p2, 100);
                    hr >= 0;
                    hr = pEvent.GetEvent(out ec, out p1, out p2, 100)
                    )
                {
                    Debug.WriteLine(ec);
                    switch (ec)
                    {
                    // If the clip is finished playing
                    case EventCode.Complete:
                    case EventCode.ErrorAbort:
                    case EventCode.UserAbort:
                        exitCode = ec;

                        // Release any resources the message allocated
                        hr = pEvent.FreeEventParams(ec, p1, p2);
                        DsError.ThrowExceptionForHR(hr);
                        break;

                    case EventCode.OleEvent:
                        string s1 = Marshal.PtrToStringBSTR(p1);
                        string s2 = Marshal.PtrToStringBSTR(p2);
                        string s3 = s2.Remove(s2.Length - 1, 1);

                        Debug.WriteLine(string.Format("OleEvent Parms: {0} | {1}", s1, s3));
                        hr = pEvent.FreeEventParams(ec, p1, p2);
                        break;

                    default:
                        // Release any resources the message allocated
                        hr = pEvent.FreeEventParams(ec, p1, p2);
                        DsError.ThrowExceptionForHR(hr);
                        break;
                    }
                }

                // If the error that exited the loop wasn't due to running out of events
                if (hr != E_ABORT)
                {
                    DsError.ThrowExceptionForHR(hr);
                }
            } while (exitCode == 0);

            pEvent = null;

            // Send an event saying we are complete
            if (Completed != null)
            {
                CompletedArgs ca = new CompletedArgs(exitCode);
                Completed(this, ca);
            }
        } // Exit the thread
Пример #17
0
        // Wait for events to happen.  This approach uses waiting on an event handle.
        // The nice thing about doing it this way is that you aren't in the windows message
        // loop, and don't have to worry about re-entrency or taking too long.  Plus, being
        // in a class as we are, we don't have access to the message loop.
        // Alternately, you can receive your events as windows messages.  See
        // IMediaEventEx.SetNotifyWindow.
        private void EventWait()
        {
            // Returned when GetEvent is called but there are no events
            const int E_ABORT = unchecked ((int)0x80004004);

            int       hr;
            IntPtr    p1, p2;
            EventCode ec;

            do
            {
                // Wait for an event
                m_mre.WaitOne(-1, true);

                // Avoid contention for m_State
                lock (this)
                {
                    // If we are not shutting down
                    if (m_State != GraphState.Exiting)
                    {
                        // Read the event
                        for (
                            hr = m_mediaEvent.GetEvent(out ec, out p1, out p2, 0);
                            hr >= 0;
                            hr = m_mediaEvent.GetEvent(out ec, out p1, out p2, 0)
                            )
                        {
                            // Write the event name to the debug window
                            Debug.WriteLine(ec.ToString());

                            // If the clip is finished playing
                            if (ec == EventCode.Complete)
                            {
                                // Call Stop() to set state
                                Stop();

                                // Throw event
                                if (StopPlay != null)
                                {
                                    StopPlay(this);
                                }
                            }

                            // Release any resources the message allocated
                            hr = m_mediaEvent.FreeEventParams(ec, p1, p2);
                            DsError.ThrowExceptionForHR(hr);
                        }

                        // If the error that exited the loop wasn't due to running out of events
                        if (hr != E_ABORT)
                        {
                            DsError.ThrowExceptionForHR(hr);
                        }
                    }
                    else
                    {
                        // We are shutting down
                        break;
                    }
                }
            } while (true);
        }
Пример #18
0
        /// <summary>
        /// Called on a new thread to process events from the graph.  The thread
        /// exits when the graph finishes.  Cancelling is done here.
        /// </summary>
        private void EventWait()
        {
            // Returned when GetEvent is called but there are no events
            const int E_ABORT = unchecked ((int)0x80004004);

            int       hr;
            IntPtr    p1, p2;
            EventCode ec;
            EventCode exitCode = 0;

            IMediaEvent pEvent = (IMediaEvent)m_pGraph;

            do
            {
                // Read the event
                for (
                    hr = pEvent.GetEvent(out ec, out p1, out p2, 100);
                    hr >= 0 && m_State < ClassState.GraphCompleted;
                    hr = pEvent.GetEvent(out ec, out p1, out p2, 100)
                    )
                {
                    switch (ec)
                    {
                    case EventCode.UserAbort:
                        ChangeState(ClassState.Cancelling);
                        exitCode = ec;
                        // Release any resources the message allocated
                        hr = pEvent.FreeEventParams(ec, p1, p2);
                        DESError.ThrowExceptionForHR(hr);

                        break;

                    // If the clip is finished playing
                    case EventCode.Complete:
                    case EventCode.ErrorAbort:
                        ChangeState(ClassState.GraphCompleting);
                        exitCode = ec;

                        // Release any resources the message allocated
                        hr = pEvent.FreeEventParams(ec, p1, p2);
                        DESError.ThrowExceptionForHR(hr);
                        break;

                    // Walked past the end of a video file, send an event
                    case EC_VideoFileComplete:
                        if (FileCompleted != null)
                        {
                            MediaFile         mf = m_Video.File(p1.ToInt32());
                            FileCompletedArgs ca = new FileCompletedArgs(mf.FileName, FileCompletedArgs.FileType.Video);
                            FileCompleted(this, ca);
                        }
                        break;

                    // Walked past the end of a video file, send an event
                    case EC_AudioFileComplete:
                        if (FileCompleted != null)
                        {
                            MediaFile         mf = m_Audio.File(p1.ToInt32());
                            FileCompletedArgs ca = new FileCompletedArgs(mf.FileName, FileCompletedArgs.FileType.Audio);
                            FileCompleted(this, ca);
                        }
                        break;

                    default:
                        // Release any resources the message allocated
                        hr = pEvent.FreeEventParams(ec, p1, p2);
                        DESError.ThrowExceptionForHR(hr);
                        break;
                    }
                }

                // If the error that exited the loop wasn't due to running out of events
                if (hr != E_ABORT)
                {
                    DESError.ThrowExceptionForHR(hr);
                }
                //FilterState fs;
                //m_pControl.GetState(200, out fs);
                ////DESError.ThrowExceptionForHR(hr);
            } while (m_State < ClassState.GraphCompleting);

            // If the user cancelled
            if (m_State == ClassState.Cancelling && m_pControl != null)
            {
                // Stop the graph, send an appropriate exit code
                hr       = m_pControl.Stop();
                exitCode = EventCode.UserAbort;
            }

            if (m_State == ClassState.GraphCompleting)
            {
                m_State = ClassState.GraphCompleted;
            }
            else
            {
                m_State = ClassState.Cancelled;
            }

            threadCompleted = true;

            // Send an event saying we are complete
            if (this.ThreadFinished != null)
            {
                DESCompletedArgs ca = new DESCompletedArgs(exitCode);
                this.ThreadFinished(this, ca);
            }
        } // Exit the thread
Пример #19
0
        public void RunGraph()
        {
            DateTime lastTick = DateTime.Now;
            int      hangPeriod = MCEBuddyConf.GlobalMCEConfig.GeneralOptions.hangTimeout;
            long     lastVideoSize = 0, lastAudioSize = 0, lastSubtitleSize = 0;
            long     totalPartsSize = 0, sourceSize = 0;
            bool     AbortError = false;
            int      hr         = 0;

            IMediaControl mediaControl = (IMediaControl)_fg;
            IMediaEvent   mediaEvent   = (IMediaEvent)_fg;

            hr = mediaControl.Run();
            checkHR(hr);

            // Change the priority temporarily (need to reset it back after Dumping Streams)
            ProcessPriorityClass lastPriority = GlobalDefs.Priority;         // Set it up

            Process.GetCurrentProcess().PriorityClass = GlobalDefs.Priority; // Set the CPU Priority
            IOPriority.SetPriority(GlobalDefs.IOPriority);                   // First set the CPU priority

            // Get filesize of source file
            sourceSize = Util.FileIO.FileSize(_SourceFile); // Sanity checking
            if (sourceSize <= 0)
            {
                _jobLog.WriteEntry(this, "Unable to get source file size, disabling infinite loop checking.", Log.LogEntryType.Warning);
                hangPeriod = 0;
            }

            bool stop = false, isSuspended = false;

            while (!stop)
            {
                System.Threading.Thread.Sleep(100);
                if (_jobStatus.Cancelled)
                {
                    // Received a shutdown command external to the filter extraction
                    _jobLog.WriteEntry(this, "Stream extraction cancelled, aborting graph.", Log.LogEntryType.Warning);
                    stop       = true;
                    AbortError = true;
                    mediaControl.Stop();
                    break;
                }

                if (isSuspended)
                {
                    lastTick = DateTime.Now;          // Since during suspension there will be no output it shouldn't terminate the process
                }
                if (!isSuspended && GlobalDefs.Pause) // Check if process has to be suspended (if not already)
                {
                    _jobLog.WriteEntry(this, "Stream extraction paused", Log.LogEntryType.Information);
                    mediaControl.Pause();
                    isSuspended = true;
                }

                if (isSuspended && !GlobalDefs.Pause) // Check if we need to resume the process
                {
                    _jobLog.WriteEntry(this, "Stream extraction resumed", Log.LogEntryType.Information);
                    isSuspended = false;
                    mediaControl.Run();
                }

                if (lastPriority != GlobalDefs.Priority) // Check if the priority was changed and if so update it
                {
                    _jobLog.WriteEntry(this, "Stream extraction priority changed", Log.LogEntryType.Information);
                    lastPriority = GlobalDefs.Priority;
                    Process.GetCurrentProcess().PriorityClass = GlobalDefs.Priority; // Set the CPU Priority
                    IOPriority.SetPriority(GlobalDefs.IOPriority);                   // First set the CPU priority
                }

                EventCode ev;
                IntPtr    p1, p2;
                if (mediaEvent.GetEvent(out ev, out p1, out p2, 0) == 0)
                {
                    if (ev == EventCode.Complete)
                    {
                        mediaControl.Stop();
                        stop = true;
                    }
                    else if (ev == EventCode.ErrorAbort || ev == EventCode.UserAbort || ev == EventCode.StErrStopped || ev == EventCode.ErrorAbortEx)
                    {
                        mediaControl.Stop();
                        stop = true;
                        //AbortError = true; - some partial/corrupted files are errored out, we'll handle extraction errors later
                    }
                    mediaEvent.FreeEventParams(ev, p1, p2);
                }

                // Sanity checking to prevent infinite loop for extraction (sometimes steams extracts infinitely)
                // Check if the filesize exceed the initial file size and if so abort the operation
                if (sourceSize > 0)
                {
                    totalPartsSize = 0;

                    // Video file check
                    if ((_extractMediaType & ExtractMediaType.Video) != 0)
                    {
                        long videoSize = Util.FileIO.FileSize(_VideoPart);
                        if (videoSize < 0)
                        {
                            _jobLog.WriteEntry(this, "Unable to get extracted video stream file size for infinite loop detection.", Log.LogEntryType.Warning);
                        }
                        else if (videoSize > (sourceSize * INFINITE_LOOP_CHECK_THRESHOLD))
                        {
                            _jobLog.WriteEntry(this, "Extracted video stream is greater than " + INFINITE_LOOP_CHECK_THRESHOLD.ToString(CultureInfo.InvariantCulture) + " times the source file size " + (sourceSize / 1024).ToString("N", CultureInfo.InvariantCulture) + " [KB].\r\nExtraction likely hung, terminating streams extraction.", Log.LogEntryType.Error);
                            stop       = true;
                            AbortError = true;
                            mediaControl.Stop();
                            break;
                        }

                        if (hangPeriod > 0)
                        {
                            if (videoSize > lastVideoSize) // If we have progress
                            {
                                lastTick = DateTime.Now;
                            }
                        }

                        totalPartsSize += videoSize;
                        lastVideoSize   = videoSize;
                    }

                    // Audio file check
                    if ((_extractMediaType & ExtractMediaType.Audio) != 0)
                    {
                        foreach (string audioPart in _AudioParts)
                        {
                            long audioSize = Util.FileIO.FileSize(audioPart);
                            if (audioSize < 0)
                            {
                                _jobLog.WriteEntry(this, "Unable to get extracted audio stream file size for infinite loop detection.", Log.LogEntryType.Warning);
                            }
                            else if (audioSize > (sourceSize * INFINITE_LOOP_CHECK_THRESHOLD))
                            {
                                _jobLog.WriteEntry(this, "Extracted audio stream is greater than " + INFINITE_LOOP_CHECK_THRESHOLD.ToString(CultureInfo.InvariantCulture) + " times the source file size " + (sourceSize / 1024).ToString("N", CultureInfo.InvariantCulture) + " [KB].\r\nExtraction likely hung, terminating streams extraction.", Log.LogEntryType.Error);
                                stop       = true;
                                AbortError = true;
                                mediaControl.Stop();
                                break;
                            }

                            if (hangPeriod > 0)
                            {
                                if (audioSize > lastAudioSize) // If we have progress
                                {
                                    lastTick = DateTime.Now;
                                }
                            }

                            totalPartsSize += audioSize;
                            lastAudioSize   = audioSize;
                        }
                    }

                    // Subtitle file check
                    if ((_extractMediaType & ExtractMediaType.Subtitle) != 0)
                    {
                        foreach (string subtitlePart in _SubtitleParts)
                        {
                            long subtitleSize = Util.FileIO.FileSize(subtitlePart);
                            if (subtitleSize < 0)
                            {
                                _jobLog.WriteEntry(this, "Unable to get extracted subtitle stream file size for infinite loop detection.", Log.LogEntryType.Warning);
                            }
                            else if (subtitleSize > (sourceSize * INFINITE_LOOP_CHECK_THRESHOLD))
                            {
                                _jobLog.WriteEntry(this, "Extracted subtitle stream is greater than " + INFINITE_LOOP_CHECK_THRESHOLD.ToString(CultureInfo.InvariantCulture) + " times the source file size " + (sourceSize / 1024).ToString("N", CultureInfo.InvariantCulture) + " [KB].\r\nExtraction likely hung, terminating streams extraction.", Log.LogEntryType.Error);
                                stop       = true;
                                AbortError = true;
                                mediaControl.Stop();
                                break;
                            }

                            if (hangPeriod > 0)
                            {
                                if (subtitleSize > lastSubtitleSize) // If we have progress
                                {
                                    lastTick = DateTime.Now;
                                }
                            }

                            totalPartsSize  += subtitleSize;
                            lastSubtitleSize = subtitleSize;
                        }
                    }

                    if (totalPartsSize < 0)
                    {
                        totalPartsSize = 0;                                                                                                                                           // Incase we get -ve numbers
                    }
                    _jobStatus.PercentageComplete = (((float)totalPartsSize / (float)sourceSize) > 1 ? 100 : ((float)totalPartsSize / (float)sourceSize) * 100);                      // Calculate % complete from size estimation (since no recoding is happening) and cap at 100%
                    _jobLog.WriteEntry(this, "Percentage complete : " + _jobStatus.PercentageComplete.ToString("0.00", CultureInfo.InvariantCulture) + " %", Log.LogEntryType.Debug); // Write to file
                }

                // Check if we have reached the end of the file or runs out of disk space, sometime windows just loops endlessly without any incremental output
                // TODO: Should we treat this as an error or normal processing
                if ((hangPeriod > 0) && (DateTime.Now > lastTick.AddSeconds(hangPeriod)))
                {
                    _jobLog.WriteEntry("No response from stream extraction for " + hangPeriod + " seconds, process likely finished, continuing.", Log.LogEntryType.Warning); // Don't treat as an error for now
                    stop = true;
                    // AbortError = true;  // Don't treat as an error for now
                    mediaControl.Stop();
                    break;
                }
            }

            // Reset Priority to Normal
            IOPriority.SetPriority(GlobalDefs.EngineIOPriority);                   // Set CPU priority after restoring the scheduling priority
            Process.GetCurrentProcess().PriorityClass = GlobalDefs.EnginePriority; // Set the CPU Priority back to Above Normal (engine always runs above normal)

            List <string> parts = _AudioParts.Concat(_SubtitleParts).ToList();     // Create a list of all subtitle, audio parts

            if (!String.IsNullOrWhiteSpace(_VideoPart))
            {
                parts.Add(_VideoPart);                                                                                                                                         // add video part
            }
            _jobLog.WriteEntry(this, "Source " + _SourceFile + " filesize [KB] : " + (sourceSize / 1024).ToString("N", CultureInfo.InvariantCulture), Log.LogEntryType.Debug); // Write to file
            foreach (string part in parts)
            {
                _jobLog.WriteEntry(this, part + " extracted filesize [KB] : " + (FileIO.FileSize(part) / 1024).ToString("N", CultureInfo.InvariantCulture), Log.LogEntryType.Debug); // Write to file
            }
            _jobLog.WriteEntry(this, "Total extracted parts size [KB] : " + (totalPartsSize / 1024).ToString("N", CultureInfo.InvariantCulture), Log.LogEntryType.Debug);            // Write to file

            if (!AbortError)
            {
                _SuccessfulExtraction = true;
            }
        }
Пример #20
0
        /// <summary>
        /// Called on a new thread to process events from the graph.  The thread
        /// exits when the graph finishes.  Cancelling is done here.
        /// </summary>
        private void EventWait()
        {
            try
            {
                // Returned when GetEvent is called but there are no events
                const int E_ABORT = unchecked ((int)0x80004004);

                int       hr;
                int       p1, p2;
                EventCode ec;
                EventCode exitCode = 0;

                IMediaEvent pEvent = (IMediaEvent)_graph;

                do
                {
                    // Read the event
                    for (
                        hr = pEvent.GetEvent(out ec, out p1, out p2, 100);
                        hr >= 0 && _state < RendererState.GraphCompleted;
                        hr = pEvent.GetEvent(out ec, out p1, out p2, 100)
                        )
                    {
                        switch (ec)
                        {
                        // If the clip is finished playing
                        case EventCode.Complete:
                        case EventCode.ErrorAbort:
                            ChangeState(RendererState.GraphStarted, RendererState.GraphCompleting);
                            exitCode = ec;

                            // Release any resources the message allocated
                            hr = pEvent.FreeEventParams(ec, p1, p2);
                            DESError.ThrowExceptionForHR(hr);
                            break;

                        default:
                            // Release any resources the message allocated
                            hr = pEvent.FreeEventParams(ec, p1, p2);
                            DESError.ThrowExceptionForHR(hr);
                            break;
                        }
                    }

                    // If the error that exited the loop wasn't due to running out of events
                    if (hr != E_ABORT)
                    {
                        DESError.ThrowExceptionForHR(hr);
                    }
                } while (_state < RendererState.GraphCompleting);

                // If the user cancelled
                if (_state == RendererState.Cancelling)
                {
                    // Stop the graph, send an appropriate exit code
                    hr       = _mediaControl.Stop();
                    exitCode = EventCode.UserAbort;
                }

                if (_state == RendererState.GraphCompleting)
                {
                    ChangeState(RendererState.GraphCompleted);
                    OnRenderCompleted();
                    if (_renderResult != null)
                    {
                        _renderResult.Complete(false);
                    }
                    if (_cancelResult != null)
                    {
                        _cancelResult.Complete(false);
                    }
                }
                else
                {
                    ChangeState(RendererState.Cancelled);
                    OnRenderCompleted();
                    if (_renderResult != null)
                    {
                        _renderResult.Complete(true);
                    }
                    if (_cancelResult != null)
                    {
                        _cancelResult.Complete(false);
                    }
                }
            }
            catch (Exception ex)
            {
                if (_renderResult != null)
                {
                    _renderResult.Complete(ex);
                }
                if (_cancelResult != null)
                {
                    _cancelResult.Complete(ex);
                }
            }
        }