Qt5Widgets.dll DLL error when it is installed to another computer

3

I'm trying to export an application built in Qt 5.7.0 (compiled to 32-bit, though development takes place in a Windows 10, 64-bit environment) to another computer (this one with Windows 8.1, 32 bit).

To do this, I have prepared the CMake script to install all dependent DLLs (using the BundleUtilities that exists in the latest versions of CMake). The script works as expected by copying the executable and DLLs to the configured path as the installation prefix.

However, by taking the generated bundle of files to the target computer and attempting to run the application there, the following error occurs:

  

[...]\Qt5Widgets.dllisnotdesignedtorunonWindows  orcontainsanerror.Trytoinstalltheprogramagainusingthemedia  theoriginalinstallationorcontactyoursystemadministratororthe  providerforsupport.Errorstatus0xc000035a.

Notes:

  • ItshouldbepossibletorealizethattheabovetestwasdoneonaWindows8.1,32-bit,installedonaVMWare(usedjustforeasiertesting).ButI'vealreadydonethetestontheactualmachineandtheerroristhesame(althoughontheactualmachinetheoperatingsystemalsocomplainsaboutQt5Core.dll,andonVMWareitonlycomplainsaboutQt5Widgets.dll).

    /li>
  • TheinstalledQtis 5.7.0, 32 bits, for Visual Studio 2015 . I've already checked and even reinstalled just to make sure I'm not using 64-bit binaries by mistake.

  • When running on the development machine, the application works normally. And this machine does not have any other version of Qt installed.

  • Although the error occurs in a Qt DLL, I have already manually installed it in VMWare VS 2015 Redistributables (32 bit). But the error persists.

  • MCVE

    Code file for executable ( teste.exe ):

    #include <QApplication>
    #include <QLabel>
    
    int main(int argc, char** argv)
    {
        QApplication oApp(argc, argv);
    
        QLabel oLabel(0, Qt::Dialog);
        oLabel.setWindowFlags(oLabel.windowFlags() & ~Qt::WindowContextHelpButtonHint);
        oLabel.setWindowTitle("Teste para o SOPt");
        oLabel.setFixedSize(400, 150);
    
        oLabel.setAlignment(Qt::AlignHCenter | Qt::AlignVCenter);
        oLabel.setText("Olá Mundo!");
        oLabel.setStyleSheet("QLabel { font-size: 50px; color: black; background: white; } QLabel:hover { color: white; background: black; }");
    
        oLabel.show();
        return oApp.exec();
    }
    

    CMake configuration file (% with%):

    cmake_minimum_required(VERSION 2.8.11)
    project(Teste)
    
    #############################################
    # Configuração
    #############################################
    
    # Tipos de build
    if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
      set(CMAKE_BUILD_TYPE Release CACHE STRING "Choose the type of build." FORCE)
      set_property(CACHE CMAKE_BUILD_TYPE PROPERTY STRINGS "Debug" "Release")
    endif()
    
    # Configuração do Qt
    set(CMAKE_INCLUDE_CURRENT_DIR ON)
    set(CMAKE_AUTOMOC ON)
    set(CMAKE_AUTORCC ON)
    set(CMAKE_AUTOUIC ON)
    find_package(Qt5Core REQUIRED)
    find_package(Qt5Widgets REQUIRED)
    
    # Arquivos de código
    file(GLOB SRC *.cpp *.h)
    
    # Prepara o executável
    if(WIN32)
        add_executable(Teste WIN32 ${SRC})
    else()
        add_executable(Teste ${SRC})
    endif()
    
    # Configura nome do target
    set_target_properties(Teste PROPERTIES OUTPUT_NAME teste)
    
    # Configura libs linkadas
    target_link_libraries(Teste Qt5::Core Qt5::Widgets)
    
    #############################################
    # Instalação
    #############################################
    
    # Instala o executável
    install(TARGETS Teste DESTINATION bin)
    
    # Instala as dependências do Qt
    set(APP "\${CMAKE_INSTALL_PREFIX}/bin/teste.exe")
    set(DIRS ${QT_LIBRARY_DIRS})
    INSTALL(CODE "
       include(BundleUtilities)
       fixup_bundle(\"${APP}\"   \"\"   \"${DIRS}\")
       ")
    
    # Instala outras dependências (VS 2015 Redistributable, etc)
    include(InstallRequiredSystemLibraries)
    

    After running CMake, it will generate the Visual Studio solution. Then, after compiling the "Test" project (which generates the binary) and compile the "Install" project (which copies the binary and the dependency DLLs to the configured folder in the installation prefix - variable CMakeLists.txt ), the folder configured for installation contains the following files:

      
    • api-ms-win-crt-environment-l1-1-0.dll
    •   
    • api-ms-win-crt-filesystem-l1-1-0.dll
    •   
    • api-ms-win-crt-heap-l1-1-0.dll
    •   
    • api-ms-win-crt-locale-l1-1-0.dll
    •   
    • api-ms-win-crt-math-l1-1-0.dll
    •   
    • api-ms-win-crt-runtime-l1-1-0.dll
    •   
    • api-ms-win-crt-stdio-l1-1-0.dll
    •   
    • api-ms-win-crt-string-l1-1-0.dll
    •   
    • api-ms-win-crt-time-l1-1-0.dll
    •   
    • api-ms-win-crt-utility-l1-1-0.dll
    •   
    • msvcp140.dll
    •   
    • Qt5Core.dll
    •   
    • Qt5Gui.dll
    •   
    • Qt5Widgets.dll
    •   
    • teste.exe
    •   
    • vcruntime140.dll
    •   
        
    asked by anonymous 02.08.2016 / 15:43

    1 answer

    3
      

    Note: The final solution was given in the edition, added to the end of this   answer.

    I kind of figured out what's going on. : / The error is in the copy made by BundleUtilities in the script of CMake (not that it is wrong, maybe it is that I did not know how to use correctly).

    As the error complains that the binary image (in this case, the DLL) is inappropriate, I used the dumpbin utility (installed along with Visual Studio on C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\bin\ path) and executed:

    dumpbin Qt5Widgets.dll /headers
    

    The result indicated that the image was actually , compiled to 64 bits (line marked with an arrow):

    Microsoft (R) COFF/PE Dumper Version 14.00.24210.0
    Copyright (C) Microsoft Corporation.  All rights reserved.
    
    
    Dump of file Qt5Widgets.dll
    
    PE signature found
    
    File Type: DLL
    
    FILE HEADER VALUES
                8664 machine (x64) <==========================
                   8 number of sections
            56F5814D time date stamp Fri Mar 25 15:19:57 2016
                   0 file pointer to symbol table
                   0 number of symbols
                  F0 size of optional header
                2022 characteristics
                       Executable
                       Application can handle large (>2GB) addresses
                       DLL
    [...]
    

    But as I said, I've confirmed that my Qt installation is 32-bit. Then I re-run the installation inscript and paid attention to the Visual Studio output:

    1>------ Build started: Project: INSTALL, Configuration: Release Win32 ------
    1>  -- Install configuration: "Release"
    1>  -- Installing: C:/temp/Data/bin/teste.exe
    1>  -- fixup_bundle
    1>  --   app='C:/temp/Data/bin/teste.exe'
    1>  --   libs=''
    1>  --   dirs=''
    1>  --   ignoreItems=''
    1>  -- fixup_bundle: preparing...
    1>  -- fixup_bundle: copying...
    1>  -- 1/28: *NOT* copying 'C:/temp/Data/bin/teste.exe'
    1>  -- 2/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/Qt5Core.dll'
    1>  -- 3/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/Qt5Gui.dll'
    1>  -- 4/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/Qt5Widgets.dll'
    1>  -- 5/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/api-ms-win-crt-environment-l1-1-0.dll'
    1>  -- 6/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/api-ms-win-crt-filesystem-l1-1-0.dll'
    1>  -- 7/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/api-ms-win-crt-heap-l1-1-0.dll'
    1>  -- 8/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/api-ms-win-crt-locale-l1-1-0.dll'
    1>  -- 9/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/api-ms-win-crt-math-l1-1-0.dll'
    1>  -- 10/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/api-ms-win-crt-runtime-l1-1-0.dll'
    1>  -- 11/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/api-ms-win-crt-stdio-l1-1-0.dll'
    1>  -- 12/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/api-ms-win-crt-string-l1-1-0.dll'
    1>  -- 13/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/api-ms-win-crt-time-l1-1-0.dll'
    1>  -- 14/28: copying 'C:/Program Files/MiKTeX 2.9/miktex/bin/x64/api-ms-win-crt-utility-l1-1-0.dll'
    1>  -- fixup_bundle: fixing...
    1>  -- 15/28: fix-up not required on this platform 'C:/temp/Data/bin/teste.exe'
    1>  -- 16/28: fix-up not required on this platform 'C:/temp/Data/bin/Qt5Core.dll'
    1>  -- 17/28: fix-up not required on this platform 'C:/temp/Data/bin/Qt5Gui.dll'
    1>  -- 18/28: fix-up not required on this platform 'C:/temp/Data/bin/Qt5Widgets.dll'
    1>  -- 19/28: fix-up not required on this platform 'C:/temp/Data/bin/api-ms-win-crt-environment-l1-1-0.dll'
    1>  -- 20/28: fix-up not required on this platform 'C:/temp/Data/bin/api-ms-win-crt-filesystem-l1-1-0.dll'
    1>  -- 21/28: fix-up not required on this platform 'C:/temp/Data/bin/api-ms-win-crt-heap-l1-1-0.dll'
    1>  -- 22/28: fix-up not required on this platform 'C:/temp/Data/bin/api-ms-win-crt-locale-l1-1-0.dll'
    1>  -- 23/28: fix-up not required on this platform 'C:/temp/Data/bin/api-ms-win-crt-math-l1-1-0.dll'
    1>  -- 24/28: fix-up not required on this platform 'C:/temp/Data/bin/api-ms-win-crt-runtime-l1-1-0.dll'
    1>  -- 25/28: fix-up not required on this platform 'C:/temp/Data/bin/api-ms-win-crt-stdio-l1-1-0.dll'
    1>  -- 26/28: fix-up not required on this platform 'C:/temp/Data/bin/api-ms-win-crt-string-l1-1-0.dll'
    1>  -- 27/28: fix-up not required on this platform 'C:/temp/Data/bin/api-ms-win-crt-time-l1-1-0.dll'
    1>  -- 28/28: fix-up not required on this platform 'C:/temp/Data/bin/api-ms-win-crt-utility-l1-1-0.dll'
    1>  -- fixup_bundle: cleaning up...
    1>  -- fixup_bundle: verifying...
    1>  -- ===========================================================================
    1>  -- Analyzing app='C:/temp/Data/bin/teste.exe'
    1>  -- bundle='C:/temp/Data/bin'
    1>  -- executable='C:/temp/Data/bin/teste.exe'
    1>  -- valid='1'
    1>  -- executable file 1: C:/temp/Data/bin/teste.exe
    1>  -- verified='1'
    1>  -- info='Verified 1 executable files in 'C:/temp/Data/bin''
    1>  --
    1>  -- verified='1'
    1>  -- info=''
    1>  --
    1>  -- fixup_bundle: done
    1>  -- Installing: C:/temp/Data/bin/msvcp140.dll
    1>  -- Installing: C:/temp/Data/bin/vcruntime140.dll
    ========== Build: 1 succeeded, 0 failed, 3 up-to-date, 0 skipped ==========
    

    Well, then I had the displeasure to realize that CMake was copying dependencies from the wrong source : it is copying from C:/Program Files/MiKTeX 2.9/miktex , which is a Miktex installation (LaTex compiler for Windows ) that I have installed here (and that also uses Qt to develop its own graphical interfaces).

      

    I will re-edit this answer in the future. I'm still trying   understand why it copied from the wrong source. My suspicion is that   it looks for the dependencies in the environment variable PATH and copies the   first thing to find - though from the documentation say nothing to   this respect (at least not clearly).

    EDITION (Final Solution)

    First, it happens that the QT_LIBRARY_DIRS variable does not exist in Qt5. Apparently, it existed in Qt4, but was deprecated in the new version since targets (such as Qt5::Core ) make it unnecessary to access the directory libraries directly (yet each target has the path of its CMake set in the variable <target>_DIR ). So, since this variable did not have the directory where BundleUtilities should get the DLLs, it simply followed some arbitrary order.

    I tested changing the order in the variable PATH , but it did not change anything (continued picking up Miktex erroneously). After spending all day studying the problem, I came to the conclusion that using BundleUtilities does not help much. The way it finds the dependencies of an executable is not clear (from what I read in the documentation it uses dumpbin itself, among other tools), and even though I reported in a hardcoded ) the directories from where he needed to get the dependencies, I found out afterwards that he simply ignored many of them.

    For example, he did not copy the plugin qwidows.dll , and even forcing the copy of that file he did not copy it to the correct folder ( ./bin/platforms ). It also did not copy some of the C Runtime DLLs (which changed in the Windows 10 version and needs to be distributed - #bummer).

    So I opted to manually copy the files myself, in order to guarantee their source without problems . The CMake script below makes this copy without using BundleUtilities . I know the ideal would be to auto-identify, but the directory from where to fetch the C Runtime DLLs needs to be set up and, for ease, I have chosen to simply send all of them (even if only a few are being used in the code).

    cmake_minimum_required(VERSION 2.8.11)
    project(Teste)
    
    #############################################
    # Configuração
    #############################################
    
    # Tipos de build
    if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
      set(CMAKE_BUILD_TYPE Release CACHE STRING "Choose the type of build." FORCE)
      set_property(CACHE CMAKE_BUILD_TYPE PROPERTY STRINGS "Debug" "Release")
    endif()
    
    # Configuração do Qt
    set(CMAKE_INCLUDE_CURRENT_DIR ON)
    set(CMAKE_AUTOMOC ON)
    set(CMAKE_AUTORCC ON)
    set(CMAKE_AUTOUIC ON)
    find_package(Qt5 REQUIRED Core Widgets)
    
    # Arquivos de código
    file(GLOB SRC *.cpp *.h)
    
    # Prepara o executável
    if(WIN32)
        add_executable(Teste WIN32 ${SRC})
    else()
        add_executable(Teste ${SRC})
    endif()
    
    # Configura nome do target
    set_target_properties(Teste PROPERTIES OUTPUT_NAME teste)
    
    # Configura libs linkadas
    target_link_libraries(Teste Qt5::Core Qt5::Widgets)
    
    #############################################
    # Instalação
    #############################################
    
    get_filename_component(QT_BIN_DIR "${Qt5_DIR}/../../../bin" ABSOLUTE)
    get_filename_component(QT_PLUGIN_DIR "${Qt5_DIR}/../../../plugins" ABSOLUTE)
    
    # Instala o executável
    install(TARGETS Teste DESTINATION bin)
    
    # Instala as dependências do Qt5
    install(FILES "${QT_BIN_DIR}/Qt5Core.dll" DESTINATION bin)
    install(FILES "${QT_BIN_DIR}/Qt5Gui.dll" DESTINATION bin)
    install(FILES "${QT_BIN_DIR}/Qt5Widgets.dll" DESTINATION bin)
    install(FILES "${QT_PLUGIN_DIR}/platforms/qwindows.dll" DESTINATION bin/platforms)
    
    # Instala as dependências do Windows 10 CRT
    if(WIN32)
        set(WIN10_CRT_REDIST_DIR "C:/Program Files (x86)/Windows Kits/10/Redist/ucrt/DLLs/x86" CACHE STRING "Path of the Windows 10 Universal C Runtime DLLs." FORCE)
    
        file(GLOB CRTFiles "${WIN10_CRT_REDIST_DIR}/*.dll")
        foreach(CRTFile ${CRTFiles})
          install(FILES ${CRTFile} DESTINATION bin)
        endforeach()
    endif()
    
    # Instala demais dependências
    include(InstallRequiredSystemLibraries)
    install(FILES ${CMAKE_INSTALL_SYSTEM_RUNTIME_LIBS} DESTINATION bin)
    
        
    02.08.2016 / 17:35