DirectShow - unable to create new threads

I'm having some weird issues with DirectShow graphics in an existing application.

A few things for the first:

  • The purpose of the chart is to download raw video from FrameGrabber with the DirectShow open interface. The graph displays the video on the right for display via VMR9, and also provides raw frames to some algorithms through ISampleGrabber (DirectShow examples).
  • The schedule was built and successfully completed in a separate project. The video is displayed well, and everyone is happy.

Now the problem arises when I integrate this into existing code. Starting with initializing the application, I first create and run the graph by starting VMR9 in windowless mode. Later in the initialization, I create a pair of worker threads through _beginthreadex. When calling _beginthreadex with a return code of 12 (without memory), when and ONLY when the graph was built and started, the failure returns with a return code.

Now the explicit answer is: I'm not in memory, or perhaps in another resource. However, at the moment when the threads are trying to start, I use ~ 420 MB of system memory 2 GB. The thread stack size is explicitly set to 1 MB. As far as I can tell, I'm not out of memory. In addition, the current application has 15 threads, so I am not creating an absurd amount.

Has anyone encountered a similar problem with DirectShow? I'm generally looking for some input, we have been trying to debug this problem for quite some time and have not been successful.

I will post any code that you need, as in most DirectShow graphs, the code is long.

Edit

In accordance with the request. I'm not sure how much of the DirectShow code is causing threads to not start. However, if I only create, but do not run the chart, the threads work fine. Therefore, I assume that the failure occurs after the call of the call. My code to run the chart is as follows:

    if (CurrentState != Stopped)
        return WrongState;

    HRESULT hr;
    printf("Attempting to run graph... ");
    Timer->Start();
    hr = pMediaControl->Run();
    if (FAILED(hr))
    {
        OAFilterState State;
        hr = pMediaControl->GetState(1000, &State);     
        if ((SUCCEEDED(hr) && State != State_Running) || FAILED(hr))
        {
            return FailedToStartGraph;
        }
    }
    CurrentState = Streaming;
    SetVMRSize();
    Timer->Stop();
    RunTime->Start();
    FrameRate->Reset();

    return NoError;

The SetVMRSize function simply resizes the VMR to its parent window:

void KontronGraph::SetVMRSize()
{
    if (CurrentState == Disconnected || VideoMode != ParentWindow)
        return;
    long lWidth, lHeight; 
    HRESULT hr = pWindowController->GetNativeVideoSize(&lWidth, &lHeight, NULL, NULL); 
    if (SUCCEEDED(hr))
    {
        RECT rcSrc, rcDest; 
        // Set the source rectangle.
        rcSrc.left = 0;
        rcSrc.right = lWidth;
        rcSrc.top = 0;
        rcSrc.bottom = lHeight;

        // Get the window client area.
        GetClientRect(MyHwnd, &rcDest); 
        // Set the destination rectangle.
        rcDest.right = rcDest.right - rcDest.left;
        rcDest.bottom = rcDest.bottom - rcDest.top;
        rcDest.left = 0;
        rcDest.top = 0;

        // Set the video position.
        hr = pWindowController->SetVideoPosition(&rcSrc, &rcDest); 
    }
}

It should be noted that pWindowController is IVMRWindowlessControl9, and pMediaControl isIMediaControl

Edit 2

Tested the code using CreateThread instead of __beginthreadex. After refusing to start threads, GetLastError () returns:

8: .

:

HANDLE worker_thread = CreateThread(0, 
Thread_Stack_Size, worker_thread_op, thread_param, 0, 0);

CreateThread:

Thread_Stack_Size = 1024 * 1024;
typedef DWORD (WINAPI *worker_thread_op_type)(LPVOID params);
+3
3

_beginthreadex CreateThread, GetLastError, , , CRT, _beginthreadex. , , , .

(DirectShow) , , , ?

:. , . , 420 ( ), , - 2GB . DirectShow , .

, , DirectShow , .

MSDN, , ( )

, . . , . , ;... . , .

+2

I don’t fully understand your explanation if this is a problem or not, but with most DirectX-related tools (which, I believe, includes DirectShow), you need to make sure that all of your related calls happen on the same thread; in other words, if you configured DirectShow on a given stream, do all your calls to it using the same stream. It has been a long time since I used DirectShow, so I'm not 100% sure that this is applicable, but it definitely solves a lot of problems with D3D, which is closely related to the technology.

FWIW.

0
source

Source: https://habr.com/ru/post/1786768/


All Articles