Compiling Qt 5.14 Under Msys2

I went down this road because I wanted to compile one simple test program so I could file a bug with GnuEmacs about how they don’t catch NumLock. This is a really old bug and they seem willing to let it rot until computers cease to exist. My test program was a KeyEvent example I stole from online then added support for NumLock. It took longer to scrape from the Internet than it did to test under Linux.


 * stolen from
 * and modified for Qt 5.14
#ifndef KEYPRESS_H
#define KEYPRESS_H


class QLabel;
class QVBoxLayout;

class KeyPress : public QWidget
    KeyPress(QWidget *parent = 0);

    void keyPressEvent(QKeyEvent *);
    void keyReleaseEvent(QKeyEvent *);

    QLabel *myLabel;
    QVBoxLayout *mainLayout;

#endif // KEYPRESS_H


 * stolen from
 * and modified for Qt 5.14
#include "keypress.h"


KeyPress::KeyPress(QWidget *parent) :
    myLabel = new QLabel("LABEL");
    mainLayout = new QVBoxLayout;


void KeyPress::keyPressEvent(QKeyEvent *event)
    if(event->key() == Qt::Key_Escape)
        myLabel->setText("You pressed ESC");

    if (event->key() == Qt::Key_NumLock)
        myLabel->setText("NumLock was pressed!!!");

void KeyPress::keyReleaseEvent(QKeyEvent *event)
    if(event->key() == Qt::Key_Escape)
        myLabel->setText("You released ESC");

    if (event->key() == Qt::Key_NumLock)
        myLabel->setText("NumLock was released***");





 * stolen from
 * and modified for Qt 5.14
#include "keypress.h"

int main(int argc, char *argv[])
    QApplication a(argc, argv);

    KeyPress *keyPress = new KeyPress();

    return a.exec();

It puts up a tiny little window. When you press the [Esc] key it displays a message. Another message when you release the key. I added a pair of messages for NumLock. The reason I went through all of this pain is I wanted to prove to these people that Qt can do it under Msys2/Windows and Linux so why can’t you just look at the code in Qt to see how they are intercepting key events. Since Qt is OpenSource, the code is there for all to see.

I had hoped there was a pre-compiled Qt development package in the Msys2 environment. After installing C/C++ compilers and a few other bits, my hopes were dashed. Adding insult to injury Qt currently only has a mkspec for 32-bit mingw.

Note: I don’t install the virus known as Windows on a bare machine as the primary OS. If I have to do anything with Windows I install it in a VM. Nobody should let that be a primary computer operating system. At least not on a computer they care about.

Open a terminal in Msys2 and type the following:

pacman -S base-devel git mercurial cvs wget p7zip
pacman -S perl ruby python2 mingw-w64-i686-toolchain mingw-w64-x86_64-toolchain

pacman -S clang
pacman -S mingw32/mingw-w64-i686-clang
pacman -S mingw64/mingw-w64-x86_64-clang
pacman -S mingw32/mingw-w64-i686-clang-analyzer
pacman -S mingw64/mingw-w64-x86_64-clang-analyzer
pacman -S mingw32/mingw-w64-i686-clang-tools-extra
pacman -S mingw64/mingw-w64-x86_64-clang-tools-extra
pacman -S mingw32/mingw-w64-i686-compiler-rt
pacman -S mingw64/mingw-w64-x86_64-compiler-rt
pacman -S mingw32/mingw-w64-i686-libblocksruntime
pacman -S mingw64/mingw-w64-x86_64-libblocksruntime

(The clang stuff is mostly to get the llvm stuff Qt is looking for.) Exit out of that terminal and open a new terminal and type

pacman -Syu

You will need to crash out of the terminal rather than typing exit once this is complete. Open a new terminal and type

pacman -Su

to complete installation. Depending on the quality of your Internet connection and the time of day, this could run a long time. You may want to add



to your pacman command. It will take even longer because it won’t be skipping the slow/sucky mirrors, but it should not fail to download. The timeout feature of pacman seems to have been written by Twitter users. It fails with a message about no bytes within 10 seconds, but only takes 2-3 seconds to do that.

If something happens and pacman crashes (happened to me once) don’t panic. There is probably a dump file, but you don’t care about that. Wait a few seconds and retry the command. If you see something like this

$ pacman -S mingw-w64-i686-qt5
error: failed to init transaction (unable to lock database)
error: could not lock database: File exists
  if you're sure a package manager is not already
  running, you can remove /var/lib/pacman/db.lck

Do this

$ rm /var/lib/pacman/db.lck
rm: remove write-protected regular empty file '/var/lib/pacman/db.lck'? y

Theoretically you are now ready to configure Qt. I unzipped Qt in a shared directory so I had to cd here:

msys2 terminal prompt

Paste this in at the prompt.

windows2unix() { local pathPcs=() split pathTmp IFS=\;; read -ra split <<< "$*"; for pathTmp in "${split[@],}"; do pathPcs+=( "/${pathTmp//+([:\\])//}" ); done; echo "${pathPcs[*]}"; }; systemrootP=$(windows2unix "$SYSTEMROOT"); export PATH="$PWD/qtbase/bin:$PWD/gnuwin32/bin:/c/msys64/mingw64/bin:/c/msys64/usr/bin:$PATH"

You need more of the path than you typically get. That takes care of it.


./configure -opensource -confirm-license -release -skip qtwebengine -skip qtvirtualkeyboard -skip qtlocation -opengl desktop -qt-sqlite -qt-zlib -qt-libjpeg -qt-libpng -qt-freetype -qt-pcre -qt-harfbuzz -nomake examples -nomake tests -prefix /usr/local/bin/qt-5-14-1 -platform win32-g++ -silent 

Keep in mind I’m working with 5.14.1. You may want a different install directory. Neither qtvirtualkeyboard nor qtlocation will compile on msys2 so you definitely need to skip them. You might want to skip the 3d too if you have no plans on using it. In a VM assigned 2 CPUs and 8 Gig of RAM it took something like 6 hours to compile.

If configure spits up about some missing dependency, don’t panic. Simply find the dependency and install it. Remember, you need the 32-bit version for this build of Qt, but you might as well install both the 32 & 64-bit versions if you have the disk space.

Before running configure again you should delete these files.

$ rm config.summary
$ rm .qmake.cache
$ rm .qmake.stash
$ rm config.cache
$ rm config.log

A nice clean configure will end like this without any messages about missing things or errors.

Note: No wayland-egl support detected. Cross-toolkit compatibility disabled.

Qt is now configured for building. Just run 'make'.
Once everything is built, you must run 'make install'.
Qt will be installed into 'C:\msys64\usr\local\bin\qt-5-14-1'.

Prior to reconfiguration, make sure you remove any leftovers from
the previous build.

Note: If your build fails and you decide to configure differently, you need to run “make clean” before you delete the files mentioned above.

mingw32-make -j 4

I only had 2 CPUs assigned to this VM but I still used 4. Please note that you need to use mingw32-make. Hours later, if your build seems to go fine

mingw32-make install

If all goes well, not a given since make install seems to build a bunch of stuff the actual make skipped, you can exit that terminal window. Don’t try to use it for anything else because you’ve jacked with the path.

path after install

Note that Msys2 automatically puts /usr/local/bin in the PATH. It’s just not polite though.

msys2 path image

You have to edit your .bash_profile

bash_profile image

Things get better after you close your terminal window and open another.

image after qmake

after make image

msys2 success image

It runs really really slow launched from the command line like that. (Probably doesn’t help being in a 2 CPU VM!) Yes, I could probably fix my Windows environment to make things better, but that wasn’t the point of this exercise. There for everyone to see is the release message from NumLock having been pressed.