Qt Sql under LGPL Despite MariaDB under GPL

The Yocto recipe gives GPL as the license of MariaDB. The Qt Sql library implements its MySQL driver with MariaDB. Hence, it would be under GPL - and so would be all applications linking Qt Sql. Businesses would have to open-source their code. A disaster! So, what's wrong?

Qt Sql under LGPL Despite MariaDB under GPL

A Strange Licensing Situation for MariaDB

The Yocto recipe mariadb_*.bb gives the license of MariaDB - a MySQL fork - as GPL-2.0-only. The MariaDB project repository confirms this.

MariaDB gets pulled into the Yocto build, if we configure the Qt Sql library to build the MySQL driver. We do this by adding sql-mysql to PACKAGECONFIG_DEFAULT in the recipe qtbase_git.bb. This makes Qt Sql depend on the package mysql5, which is provided by the recipe mariadb_*.bb. This recipe also provides the package libmysqlclient, which installs /usr/lib/libmariadb.so.3 on the target device. The MySQL driver of Qt Sql turns out to be a MariaDB driver, which is also suggested by the Qt documentation.

MariaDB uses a client-server architecture. The client is the library libmariadb provided by the package libmysqlclient. An application links to the client library directly or indirectly through a library like Qt Sql. The application runs on the target. It communicates through the client library with the server, which runs in a separate process on the target or on any remote computer.

If libmariadb were under GPL-2.0, combinations with LGPL-3.0 software would be illegal and proprietary and other software would be forced under GPL-2.0.

The problem is that a proprietary application links to libmariadb, which seems to be under GPL-2.0-only. Hence, we would have to open-source the code of the proprietary application. This would be a disaster for almost all businesses, as the application is their competitive advantage. Putting MariaDB under GPL could be ploy to force users into the commercial offering. Or, the MariaDB authors could be sloppy about the license term. This deserves a thorough license analysis of the source code.

Checking the License of the MariaDB Client Library

We find the source code of MariaDB in the directory

build/tmp/work/armv8a-tdx-linux/mariadb/10.11.9/    # package work dir
    mariadb-10.11.9/                                # source dir

We change to the source directory and check README.md for licensing information. README.md reiterates in the section Licensing what we already know: MariaDB is licensed under GPL-2.0-only. README.md points us to the files COPYING and THIRDPARTY for more licensing information. COPYING contains the text of the GPL-2.0. THIRDPARTY doesn't help us with libmariadb.

In the source directory, we see a subdirectory libmariadb. The first sentence in README is promising.

This is LGPL MariaDB client library that can be used to connect to a 
MariaDB or MySQL database server.

COPYING.LIB contains the text of the LGPL-2.1. The intent of the MariaDB authors is clear: They want the client library libmariadb to be under LGPL-2.1.

Should we trust the authors and stop our license analysis at this point? I would say no. The authors were neither diligent nor helpful with licensing information. Moreover, one file under GPL is enough to put all of libmariadb under GPL.

Let us familiarise ourselves with the directory structure of the subdirectory libmariadb.

benchmark/      IGNORE
client/         *.c
external/
    zlib/       *.c *.h
include/        *.h
libmariadb/     *.c
plugins/
    auth/       *.c *.h
    compress/   *.c *.h
    connection/ *.c *.h
    io/         *.c *.h
    pvio/       *.c *.h
    trace/      *.c *.h
unittest/       IGNORE

We ignore the directories benchmark and unittest, because their artefacts will not be installed in the final product. Furthermore, we ignore all files only needed for the build: for example, CMakeLists.txt.

We must ensure that none of the C source and header files going into libmariadb or its dependencies is under GPL. The right find and grep commands will do the trick. In order to find the right search terms, we peak into some source and header files in libmariadb/ and include/. The files include/mariadb_com.h and libmariadb/mariadb_lib.c, for example, contain the following license header.

   This library is free software; you can redistribute it and/or
   modify it under the terms of the GNU Library General Public
   License as published by the Free Software Foundation; either
   version 2 of the License, or (at your option) any later version.

These files are under version 2 or any later version of the "GNU Library General Public License". In short, they are under LGPL-2.0-or-later. Similarly, files under GPL contain the term "GNU General Public License". Files under LGPL-2.1 or LGPL-3.0 contain the term "GNU Lesser General Public License". This gives us the following search terms:

  • "GNU Library" for LGPL-2.0,
  • "GNU Lesser" for LGPL-2.1 and LGPL-3.0, and
  • "GNU General" for GPL-2.0 and GPL-3.0.

As we want to rule out any source files under GPL, we fire off a search for "GNU General".

$ find . -name "*.c" -o -name "*.h" | xargs grep -l "GNU General"
./include/ma_context.h
./include/mariadb_async.h
./libmariadb/ma_context.c
./libmariadb/ma_dtoa.c
./unittest/*/*.[ch]

Option -l outputs the names of the files that contain the search term. Option -L does the opposite: It outputs the names of the files that do not contain the search term.

As mentioned already, we can ignore the files in unittest. The first four files need a closer look. We will find out that the first three files are under LGPL-2.1-or-later and the fourth file under LGPL-2.0-or-later. The match comes from the erroneous text at the beginning of the files:

  You should have received a copy of the GNU General Public License
  along with this.  If not, see <http://www.gnu.org/licenses/>.
*/

It should correctly refer to a copy of the GNU Library or GNU Lesser General Public License.

👍
libmariadb does not contain any source files under GPL.

We do a counter check to see that all C files in the directories include/ and libmariadb are under LGPL-2.0 or LGPL-2.1.

$ find include/ libmariadb/ -name "*.c" -o -name "*.h" | wc -l
72
$ find include/ libmariadb/ -name "*.c" -o -name "*.h" | xargs grep -l "GNU Lesser\|GNU Library" | wc -l
63

In total, there are 72 files matching .c or .h, but there are only 63 files under LGPL-2.0 or LGPL-2.1. 2 of the additional 9 files are under BSD-2-clause and the remaining 7 files have no license at all. So far, the license expression for the subdirectories libmariadb and include is:

include/         LGPL-2.0-or-later & LGPL-2.1-or-later & BSD-2-clause
libmariadb/      LGPL-2.0-or-later & LGPL-2.1-or-later & BSD-2-clause

Files under LGPL-2.1-or-later cannot be licensed under LGPL-2.0 but files under LGPL-2.0-or-later can be licensed under LGPL-2.1. LGPL dominates permissive licenses like BSD-2-clause. Hence, the resolved license for both directories is LGPL-2.1-or-later.

This leaves us with the C files in external/ and plugins/. An analysis similar to the one above reveals:

external/        => Zlib
    zlib/        Zlib (permissive)
plugins/         => LGPL-2.0-or-later & BSD-2-clause & BSD-3-clause
    auth/        LGPL-2.0-or-later & BSD-2-clause
    compress/    LGPL-2.0-or-later
    connection/  LGPL-2.0-or-later
    io/          BSD-3-clause
    pvio/        LGPL-2.0-or-later
    trace/       LGPL-2.0-or-later

LGPL dominates the permissive licenses Zlib, BSD-2-clause and BSD-3-clauses. Hence, the resolved license for all directories is LGPL-2.0-or-later.

👍
The resolved license for all source code that is deployed on the target device is LGPL-2.1-or-later. This confirms the license LGPL-2.1 from COPYING.LIB and refines it to LGPL-2.1-or-later.

The resolved licenses of the ignored subdirectories are:

benchmark/        No license
unittest/         GPL-2.0-only

The resolved license for the library libmariadb is:

GPL-2.0-only & LGPL-2.1-or-later

The remaining source code of MariaDB is under GPL-2.0-only, as well. Here is the final result.

👍
The Yocto recipe mariadb_*.bb should give the license term as GPL-2.0-only & LGPL-2.1-or-later.

The license situation is clear now. libmariadb is under LGPL-2.1-or-later. Hence, the proprietary application can stay closed-source under a commercial license. The library libQtSql and the plugin libqsqlmysql can stay under LGPL-3.0-only. As MariaDBMS and the application run in separate processes A and B, respectively, the GPL of MariaDBMS has no effect on the proprietary application.

As libmariadb is under LGPL-2.1-or-later, the applications and libraries linking to it can stay under their own licenses. The proprietary application can stay closed-source.

How to Reduce the Effort for License Compliance Checks

Phew! That was a lot of work to figure out the correct license term for MariaDB and to determine which parts of MariaDB are under which license. But it was worth the effort. If libmariadb were under GPL-2.0-only, we would be forbidden to release the application because of the incompatibility between LGPL-3.0-only and GPL-2.0-only. Even license-compatible SQL libraries wouldn't help, because the application would have been under GPL-2.0-only. We would have to open-source the source code of the application.

We must do such a detailed license analysis for every package with some parts licensed under GPL and some parts under any other license. The license term of such packages contains expressions like GPL & LGPL, GPL & BSD and GPL & MIT.

👉
I have done such a detailed analysis for more than 100 packages and stored the results in a license compliance database. You get this compliance database, when you purchase Option 2 of my offering License Compliance for Embedded Linux Systems.

The maintainers of open-source packages like MariaDB could also play their part in reducing the effort for license compliance. In a README or LICENSE file, they could specify which parts are under which license. They could also replace the lengthy license headers in the source files by SPDX license identifiers. The new license header of include/mariadb_async.h would look like this:

/* Copyright (C) ...
                 
   SPDX-License-Identifier: LGPL-2.1-or-later
*/

These identifiers would make automation so much easier and bring the risk of errors so much closer to zero.

Read next

Running Wayland Clients as Non-Root Users

Many embedded Linux systems use a Wayland compositor like Weston for window management. Qt applications act as Wayland clients. Weston composes the windows of the Qt applications into a single window and displays it on a screen. I still have