From 466479992de166dc9439dc95ee752f94ee75ec24 Mon Sep 17 00:00:00 2001 From: Robert Adam Date: Fri, 24 Apr 2020 11:08:58 +0200 Subject: [PATCH] src/murmur/Messages.cpp: Restrict string sizes for Version information Before this commit it was possible to pass more or less arbitrary sized strings as part of the Version message. This could lead to malicious clients sending huge strings as part of this message. The problem arises once these Strings are displayed in the UI (e.g. once a user selects Information from the context menu of such a malicious client). Qt will then be so busy to render this String that it completely freezes the UI (#4067). This commit prevents this attack by restricting the size of the Version strings on the server side. If a client sends strings that exceed this size, the server will drop the original content and replace it with a generic "[[Invalid]]". --- src/murmur/Messages.cpp | 29 +++++++++++++++++++++++------ 1 file changed, 23 insertions(+), 6 deletions(-) diff --git a/src/murmur/Messages.cpp b/src/murmur/Messages.cpp index e0bc8b10e..80189b5a0 100644 --- a/src/murmur/Messages.cpp +++ b/src/murmur/Messages.cpp @@ -1807,17 +1807,34 @@ void Server::msgContextAction(ServerUser *uSource, MumbleProto::ContextAction &m emit contextAction(uSource, u8(msg.action()), session, id); } +/// @param str The std::string to convert +/// @param maxSize The maximum allowed size for this string +/// @returns The given std::string converted to a QString, if its size is less +/// than or equal to the given maxSize. If it is bigger, "[[Invalid]]" +/// is returned. +QString convertWithSizeRestriction(const std::string &str, size_t maxSize) { + if (str.size() > maxSize) { + return QLatin1String("[[Invalid]]"); + } + + return QString::fromStdString(str); +} + void Server::msgVersion(ServerUser *uSource, MumbleProto::Version &msg) { RATELIMIT(uSource); - if (msg.has_version()) + if (msg.has_version()) { uSource->uiVersion=msg.version(); - if (msg.has_release()) - uSource->qsRelease = u8(msg.release()); + } + if (msg.has_release()) { + uSource->qsRelease = convertWithSizeRestriction(msg.release(), 100); + } if (msg.has_os()) { - uSource->qsOS = u8(msg.os()); - if (msg.has_os_version()) - uSource->qsOSVersion = u8(msg.os_version()); + uSource->qsOS = convertWithSizeRestriction(msg.os(), 40); + + if (msg.has_os_version()) { + uSource->qsOSVersion = convertWithSizeRestriction(msg.os_version(), 60); + } } log(uSource, QString("Client version %1 (%2 %3: %4)").arg(MumbleVersion::toString(uSource->uiVersion)).arg(uSource->qsOS).arg(uSource->qsOSVersion).arg(uSource->qsRelease));