Improve the message-splitting algorithm for PRIVMSG and CTCP
authorMichael Marley <michael@michaelmarley.com>
Sat, 21 Feb 2015 12:33:57 +0000 (07:33 -0500)
committerManuel Nickschas <sputnick@quassel-irc.org>
Thu, 23 Apr 2015 20:01:28 +0000 (22:01 +0200)
commit5824da2a38a9b01067e6b484ce4f8395859a44cb
tree64c4fb4e3ffb16d3c383ddd775fbea8c9324e711
parent1d69ec1e0acc6522d292ce47a7fac18636ab2d49
Improve the message-splitting algorithm for PRIVMSG and CTCP

This introduces a new message splitting algorithm based on
QTextBoundaryFinder.  It works by first starting with the entire
message to be sent, encoding it, and checking to see if it is over
the maximum message length.  If it is, it uses QTBF to find the
word boundary most immediately preceding the maximum length.  If no
suitable boundary can be found, it falls back to searching for
grapheme boundaries.  It repeats this process until the entire
message has been sent.

Unlike what it replaces, the new splitting code is not recursive
and cannot cause stack overflows.  Additionally, if it is unable
to split a string, it will give up gracefully and not crash the
core or cause a thread to run away.

This patch fixes two bugs.  The first is garbage characters caused
by accidentally splitting the string in the middle of a multibyte
character.  Since the new code splits at a character level instead
of a byte level, this will no longer be an issue.  The second is
the core crash caused by sending an overlength CTCP query ("/me")
containing only multibyte characters.  This bug was caused by the
old CTCP splitter using the byte index from lastParamOverrun() as
a character index for a QString.
src/core/corebasichandler.cpp
src/core/corebasichandler.h
src/core/corenetwork.cpp
src/core/corenetwork.h
src/core/coreuserinputhandler.cpp
src/core/coreuserinputhandler.h
src/core/ctcpparser.cpp