Как могла простая загрузка dll привести к 100 загрузке процессора в моем основном приложении?

У меня есть отлично работающая программа, которая подключается к видеокамере (камера IDS uEye) и непрерывно берет с нее кадры и отображает их.

Однако при загрузке определенной dll перед подключением к камере программа работает со 100% загрузкой процессора. Если я загружаю dll после подключения к камере, программа работает нормально.

int main()
{
    INT nRet = IS_NO_SUCCESS;
    // init camera (open next available camera)
    m_hCam = (HIDS)0;

    // (A) Uncomment this for 100% CPU load:
    // HMODULE handle = LoadLibrary(L"myInnocentDll.dll");

    // This is the call to the 3rdparty camera vendor's library:
    nRet = is_InitCamera(&m_hCam, 0);    

    // (B) Uncomment this instead of (A) and the CPU load won't change
    // HMODULE handle = LoadLibrary(L"myInnocentDll.dll");

    if (nRet == IS_SUCCESS)
    {
        /*
         * Please note: I have removed all lines which are not necessary for the exploit.
         * Therefore this is NOT a full example of how to properly initialize an IDS camera!
         */
        is_GetSensorInfo(m_hCam, &m_sInfo);

        GetMaxImageSize(m_hCam, &m_s32ImageWidth, &m_s32ImageHeight);

        m_nColorMode = IS_CM_BGR8_PACKED;// IS_CM_BGRA8_PACKED;
        m_nBitsPerPixel = 24; // 32;
        nRet |= is_SetColorMode(m_hCam, m_nColorMode);

        // allocate image memory.
        if (is_AllocImageMem(m_hCam, m_s32ImageWidth, m_s32ImageHeight, m_nBitsPerPixel, &m_pcImageMemory, &m_lMemoryId) != IS_SUCCESS)
        {
            return 1;
        }
        else
        {
            is_SetImageMem(m_hCam, m_pcImageMemory, m_lMemoryId);
        }
    }
    else
    {
        return 1;
    }

    std::thread([&]() {
        while (true) {
            is_FreezeVideo(m_hCam, IS_WAIT);
            /*
             * Usually, the image memory would now be grabbed via is_GetImageMem().
             * but as it is not needed for the exploit, I removed it as well
             */
        }
        }).detach();

    cv::waitKey(0);
}

Независимо от фактически используемого драйвера камеры, каким образом загрузка DLL может изменить ее производительность, занимая 100% всех доступных ядер ЦП? При использовании средств диагностики Visual Studio избыточное время ЦП приписывается "[Внешний вызов] SwitchToThread", а не myInnocentDll.

Загрузка только dll без инициализации камеры не приводит к 100% загрузке процессора.

Сначала я подумал о некоторых статических инициализаторах в myInnocentDll.dll, настраивающих поведение потоковой передачи, но я не нашел ничего, указывающего в этом направлении. Какие аспекты следует искать в коде myInnocentDll.dll?

2 ответа

Вы можете отключить состояние простоя процессора в диспетчере камеры IDS, и тогда минимальная загрузка процессора в планах энергопотребления Windows будет установлена ​​на 100%.

Думаю, об этом стоит здесь упомянуть, даже если вы уже решили свою проблему.

После долгих поисков я нашел ответ, и он одновременно удручающе прост и разочаровывает сам по себе:

Это слабая поддержка OpenMP со стороны Microsoft. Когда я отключил OpenMP в своем проекте, драйвер камеры работает нормально.

Причина, по-видимому, в том, что компилятор Microsoft использует OpenMP с ожиданием занятости, а также есть возможность вручную настроить OMP_WAIT_POLICY, но поскольку я все равно не зависел от OpenMP, отключение было для меня самым простым решением.

Я до сих пор не понимаю, почему ЦП поднялся только при использовании камеры, а не при запуске остальной части моего решения, даже если библиотека камеры предварительно создана, и мое отключение / включение компиляции OpenMP не может повлиять на нее.. И я также не понимаю, почему они потрудились сделать исправление для VS2010, но у меня нет реального исправления с VS2019, которое я использую. Но проблема предотвращена.

Другие вопросы по тегам