I've got Akonadi 5.17.2 -- that's the version corresponding to tag v21.04.2 so it's a bit weird there's no Bugzilla version for that. The underlying MySQL library is mysql-client 5.7.34. Starting akonadiserver (e.g. on the command line) produces a bunch of output about tables, and then: ``` org.kde.pim.akonadiserver: Running DB initializer org.kde.pim.akonadiserver: DB initializer done Connecting to deprecated signal QDBusConnectionInterface::serviceOwnerChanged(QString,QString,QString) Assertion failed: (param->buffer_length != 0), function setup_one_fetch_function, file /wrkdirs/usr/ports/databases/mysql57-client/work/mysql-5.7.34/libmysql/libmysql.c, line 4112. QSocketNotifier: Invalid socket 6 and type 'Read', disabling... ``` Akonadi is completely non-functional (because it doesn't start) with this mysql client-library version. Library version 5.7.32 does work.
With some additional debugging added, and a mutex lock on QueryBuilder::exec() so it is singlethreaded, I get this output (as an indication what Akonadi is building up): ``` org.kde.pim.akonadiserver: Prepared new query for "SELECT PartTable.id, PartTable.pimItemId, PartTable.partTypeId, PartTable.data, PartTable.datasize, PartTable.version, PartTable.storage FROM PartTable WHERE ( PartTable.partTypeId = :0 AND storage = :1 AND data IS NOT NULL )" org.kde.pim.akonadiserver: Bound 0 QVariant(qlonglong, 1) org.kde.pim.akonadiserver: Bound 1 QVariant(qlonglong, 1) Assertion failed: (param->buffer_length != 0), function setup_one_fetch_function, file /wrkdirs/usr/ports/databases/mysql57-client/work/mysql-5.7.34/libmysql/libmysql.c, line 4112. ``` and this slightly-more-detailed backtrace: ``` #0 thr_kill () at thr_kill.S:4 #1 0x0000000800ff71b4 in __raise (s=s@entry=6) at /usr/src/src/lib/libc/gen/raise.c:52 #2 0x00000008010ac129 in abort () at /usr/src/src/lib/libc/stdlib/abort.c:67 #3 0x0000000800fda0c1 in __assert (func=<optimized out>, file=<optimized out>, line=<optimized out>, failedexpr=<optimized out>) at /usr/src/src/lib/libc/gen/assert.c:51 #4 0x0000000805efeb77 in ?? () from /usr/local/lib/mysql/libmysqlclient.so.20 #5 0x0000000805efe5ce in mysql_stmt_bind_result () from /usr/local/lib/mysql/libmysqlclient.so.20 #6 0x000000080325fe6f in ?? () from /usr/local/lib/qt5/plugins/sqldrivers/libqsqlmysql.so #7 0x0000000800756da7 in QSqlQuery::exec() () from /usr/local/lib/qt5/libQt5Sql.so.5 #8 0x00000000003b9745 in Akonadi::Server::QueryBuilder::exec ( this=<optimized out>) at /zbigone/src/kde/invent/akonadi/src/server/storage/querybuilder.cpp:418 #9 0x00000000003b4d86 in Akonadi::Server::PartHelper::remove (column=..., value=...) at /zbigone/src/kde/invent/akonadi/src/server/storage/parthelper.cpp:108 #10 0x0000000000359fbb in Akonadi::Server::DataStore::unhideAllPimItems ( this=<optimized out>) at /zbigone/src/kde/invent/akonadi/src/server/storage/datastore.cpp:1177 #11 0x00000000002749f1 in Akonadi::Server::AkonadiServer::init ( this=0x7fffffffd158) at /zbigone/src/kde/invent/akonadi/src/server/akonadi.cpp:152 ```
Relevant code change between 5.7.33 and 5.7.34 is in libmysql.c, line 4112: === 5.7.33 case MYSQL_TYPE_BLOB: case MYSQL_TYPE_BIT: DBUG_ASSERT(param->buffer_length != 0); === 5.7.34 case MYSQL_TYPE_BLOB: case MYSQL_TYPE_BIT: assert(param->buffer_length != 0); As you can see the DBUG_ASSERT has turned into a "real" assert. By modifying the Qt MySQL drivers, e.g. void QMYSQLResultPrivate::bindBlobs() I can get the Qt layer to confirm that the value being passed in is 0. Apparently max_length for the field that is causing problems here, is indeed 0. By nudging that to 1, like so: ``` if (!bind->buffer_length) { bind->buffer_length=1; qWarning("QMYSQLResultPrivate::bindBlobs: field max_length was 0"); } ``` Akonadi works again (because of the patch in Qt). I'm just not convinced that's a good fix: why is there a BLOB field of length 0, anyway?
I ended up patching the mysql driver in Qt as follows: ``` - if (qIsBlob(inBinds[i].buffer_type) && meta && fieldInfo) { + if (qIsBlob(inBinds[i].buffer_type) && meta && fieldInfo && fieldInfo->max_length) { ``` It **seems** to do the trick for akonadi, at least.
Closing because - the problem seems to live somewhere other than Akonadi itself (even if Akonadi triggers it) - as "upstream" because the issue is in the Qt MySQL plugin - the problem is patched downstream.