aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDominik Holland <dominik.holland@pelagicore.com>2019-08-28 11:22:38 +0200
committerDominik Holland <dominik.holland@pelagicore.com>2019-08-30 21:16:08 +0200
commit582c91cda2c2831f666fa99d39e4637d7828927f (patch)
tree0d51216c703e843b32e2a62866106b42b440278f
parent83720c2961b7af019643f5318d84a4ea443a5a87 (diff)
geniviextras: Make QDltRegistrator more thread-safe
Introduce a mutex to prevent issues when registering a new context/application while logging from another thread. Change-Id: I734b2a363ffe83fc9e9728898707cdefef689824 Reviewed-by: Robert Griebl <robert.griebl@pelagicore.com>
-rw-r--r--src/geniviextras/qdltregistration.cpp48
-rw-r--r--src/geniviextras/qdltregistration_p.h7
2 files changed, 43 insertions, 12 deletions
diff --git a/src/geniviextras/qdltregistration.cpp b/src/geniviextras/qdltregistration.cpp
index 188b01f..8f2f080 100644
--- a/src/geniviextras/qdltregistration.cpp
+++ b/src/geniviextras/qdltregistration.cpp
@@ -55,7 +55,13 @@ QT_BEGIN_NAMESPACE
void qtGeniviLogLevelChangedHandler(char context_id[], uint8_t log_level, uint8_t trace_status)
{
- globalDltRegistration()->d_ptr->dltLogLevelChanged(context_id, log_level, trace_status);
+ auto d = globalDltRegistration()->d_ptr;
+ d->m_mutex.lock();
+ const QLoggingCategory *category = d->dltLogLevelChanged(context_id, log_level, trace_status);
+ d->m_mutex.unlock();
+
+ if (category)
+ emit globalDltRegistration()->logLevelChanged(category);
}
Q_GLOBAL_STATIC(QDltRegistration, dltRegistration)
@@ -149,6 +155,14 @@ void QDltRegistrationPrivate::registerApplication()
m_dltAppRegistered = true;
}
+void QDltRegistrationPrivate::unregisterApplication()
+{
+ if (m_dltAppRegistered)
+ DLT_UNREGISTER_APP();
+
+ m_dltAppRegistered = false;
+}
+
void QDltRegistrationPrivate::setDefaultCategory(const QString &category)
{
Q_ASSERT_X(m_categoryInfoHash.contains(category), "setDefaultContext", "The category needs to be registered as a dlt logging category before it can be set as a default context");
@@ -171,11 +185,12 @@ DltContext *QDltRegistrationPrivate::context(const char *categoryName)
return info.m_context;
}
-void QDltRegistrationPrivate::dltLogLevelChanged(char context_id[], uint8_t log_level, uint8_t trace_status)
+const QLoggingCategory * QDltRegistrationPrivate::dltLogLevelChanged(char context_id[], uint8_t log_level, uint8_t trace_status)
{
- Q_Q(QDltRegistration);
Q_UNUSED(trace_status)
+ const QLoggingCategory *changedCategory = nullptr;
+
for (auto it = m_categoryInfoHash.begin(); it != m_categoryInfoHash.end(); ++it) {
if (it.value().m_ctxName != context_id)
continue;
@@ -218,11 +233,13 @@ void QDltRegistrationPrivate::dltLogLevelChanged(char context_id[], uint8_t log_
QLoggingCategory* category = it.value().m_category;
if (category->isEnabled(type) != enabled) {
category->setEnabled(type, enabled);
- emit q->logLevelChanged(category);
+ changedCategory = category;
}
}
break;
}
+
+ return changedCategory;
}
DltLogLevelType QDltRegistrationPrivate::category2dltLevel(const QLoggingCategory *category)
@@ -320,8 +337,10 @@ void QDltRegistration::registerApplication(const char *dltAppID, const char *dlt
{
Q_D(QDltRegistration);
bool registerCategories = false;
+ QMutexLocker l(&d->m_mutex);
+
if (d->m_dltAppRegistered) {
- unregisterApplication();
+ d->unregisterApplication();
registerCategories = true;
}
@@ -352,6 +371,7 @@ void QDltRegistration::registerCategory(const QLoggingCategory *category, const
Q_D(QDltRegistration);
Q_ASSERT(category);
Q_ASSERT(strlen(category->categoryName()) != 0);
+ QMutexLocker l(&d->m_mutex);
d->registerCategory(category, new DltContext, dltCtxName, dltCtxDescription);
}
@@ -367,6 +387,7 @@ void QDltRegistration::registerCategory(const QLoggingCategory *category, const
void QDltRegistration::setDefaultContext(const char *categoryName)
{
Q_D(QDltRegistration);
+ QMutexLocker l(&d->m_mutex);
d->setDefaultCategory(QString::fromLatin1(categoryName));
}
@@ -382,6 +403,7 @@ void QDltRegistration::setDefaultContext(const char *categoryName)
void QDltRegistration::setRegisterContextOnFirstUseEnabled(bool enabled)
{
Q_D(QDltRegistration);
+ QMutexLocker l(&d->m_mutex);
d->m_registerOnFirstUse = enabled;
}
@@ -400,6 +422,7 @@ void QDltRegistration::registerUnregisteredContexts()
std::cout << "REGISTERING UNREGISTERED CONTEXTS" << std::endl;
#endif
Q_D(QDltRegistration);
+ QMutexLocker l(&d->m_mutex);
if (!d->m_dltAppRegistered)
d->registerApplication();
for (auto it = d->m_categoryInfoHash.begin(); it != d->m_categoryInfoHash.end(); ++it) {
@@ -412,12 +435,14 @@ void QDltRegistration::registerUnregisteredContexts()
void QDltRegistration::setLongMessageBehavior(QDltRegistration::LongMessageBehavior config)
{
Q_D(QDltRegistration);
+ QMutexLocker l(&d->m_mutex);
d->m_longMessageBehavior = config;
}
QDltRegistration::LongMessageBehavior QDltRegistration::longMessageBehavior() const
{
Q_D(const QDltRegistration);
+ QMutexLocker l(&d->m_mutex);
return d->m_longMessageBehavior;
}
@@ -428,10 +453,8 @@ QDltRegistration::LongMessageBehavior QDltRegistration::longMessageBehavior() co
void QDltRegistration::unregisterApplication()
{
Q_D(QDltRegistration);
- if (d->m_dltAppRegistered)
- DLT_UNREGISTER_APP();
-
- d->m_dltAppRegistered = false;
+ QMutexLocker l(&d->m_mutex);
+ d->unregisterApplication();
}
/*!
@@ -450,11 +473,14 @@ void QDltRegistration::unregisterApplication()
*/
void QDltRegistration::messageHandler(QtMsgType msgType, const QMessageLogContext &msgCtx, const QString &msg)
{
+ QMutexLocker l(&globalDltRegistration()->d_ptr->m_mutex);
+
DltContext *dltCtx = globalDltRegistration()->d_ptr->context(msgCtx.category);
if (!dltCtx)
return;
DltLogLevelType logLevel = globalDltRegistration()->d_ptr->severity2dltLevel(msgType);
+ LongMessageBehavior longMessageBehavior = globalDltRegistration()->d_ptr->m_longMessageBehavior;
const QByteArray fullMessage = qFormatLogMessage(msgType, msgCtx, msg).toUtf8();
@@ -462,13 +488,13 @@ void QDltRegistration::messageHandler(QtMsgType msgType, const QMessageLogContex
#if GENIVIEXTRAS_DEBUG
std::cout << "LOG MESSAGE TOO LONG" << std::endl;
#endif
- if (globalDltRegistration()->longMessageBehavior() == LongMessageBehavior::Truncate) {
+ if (longMessageBehavior == LongMessageBehavior::Truncate) {
#if GENIVIEXTRAS_DEBUG
std::cout << "TRUNCATE" << std::endl;
#endif
DLT_LOG(*dltCtx, logLevel, DLT_UTF8(QtGeniviExtrasPrivate::utf8_mid(fullMessage, 0, QtGeniviExtrasPrivate::MAX_MSG_LEN)));
return;
- } else if (globalDltRegistration()->longMessageBehavior() == LongMessageBehavior::Split) {
+ } else if (longMessageBehavior == LongMessageBehavior::Split) {
#if GENIVIEXTRAS_DEBUG
std::cout << "SPLIT" << std::endl;
#endif
diff --git a/src/geniviextras/qdltregistration_p.h b/src/geniviextras/qdltregistration_p.h
index 396e3a0..98542f4 100644
--- a/src/geniviextras/qdltregistration_p.h
+++ b/src/geniviextras/qdltregistration_p.h
@@ -44,6 +44,7 @@
#include <qdltregistration.h>
#include <QString>
#include <QHash>
+#include <QMutex>
#include <dlt.h>
@@ -81,15 +82,17 @@ public:
void registerCategory(const QLoggingCategory *category, DltContext *dltContext, const char *dltCtxName, const char *dltCtxDescription);
void registerCategory(CategoryInfo &info);
void registerApplication();
+ void unregisterApplication();
void setDefaultCategory(const QString &category);
DltContext *context(const char *categoryName);
- void dltLogLevelChanged(char context_id[], uint8_t log_level, uint8_t trace_status);
+ const QLoggingCategory *dltLogLevelChanged(char context_id[], uint8_t log_level, uint8_t trace_status);
static DltLogLevelType category2dltLevel(const QLoggingCategory *category);
static DltLogLevelType severity2dltLevel(QtMsgType type);
private:
+ mutable QMutex m_mutex;
QDltRegistration *const q_ptr;
Q_DECLARE_PUBLIC(QDltRegistration)
QString m_dltAppID;
@@ -99,6 +102,8 @@ private:
QHash<QString, CategoryInfo> m_categoryInfoHash;
bool m_registerOnFirstUse;
QDltRegistration::LongMessageBehavior m_longMessageBehavior;
+
+ friend void qtGeniviLogLevelChangedHandler(char context_id[], uint8_t log_level, uint8_t trace_status);
};
QT_END_NAMESPACE