qdlt: fix correctness and safety bugs in argument and segmented-msg p…#804
Open
SoundMatt wants to merge 1 commit into
Open
qdlt: fix correctness and safety bugs in argument and segmented-msg p…#804SoundMatt wants to merge 1 commit into
SoundMatt wants to merge 1 commit into
Conversation
…arsing Two unrelated bugs in qdlt/, both real and reachable, both small fixes: 1. qdlt/qdltargument.cpp:701 — QDltArgument::setValue, QVariant::Double branch: `double bvalue = value.toInt();` instead of `value.toDouble()`. Fractional part is silently truncated; large floats are clamped to integer range. Single-character correctness fix. 2. qdlt/qdltsegmentedmsg.cpp:154 — QDltSegmentedMsg::add: the chunk offset is computed as `sequence * chunkSize` in uint32_t. Both `sequence` and `chunkSize` come from the wire (start-segment and chunk-segment messages respectively); a crafted pair where `sequence < chunks` is satisfied but the product wraps gives payload.replace() a small offset and corrupts the wrong region of the resized payload buffer. Compute the offset in quint64 to avoid the wrap, and reject any chunk whose end (chunk_offset + chunkSize) would extend past the resized payload size. Cast back to int for the replace() call after the bound check has guaranteed it fits. No behaviour change for well-formed messages. Signed-off-by: Matt Jones <47545907+SoundMatt@users.noreply.github.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Problem
Two unrelated but small bugs in
qdlt/, both real and reachable:1.
QDltArgument::setValue—toInt()instead oftoDouble()qdlt/qdltargument.cpp:699–705:When a
QVariant::Doubleis passed tosetValue(), the code readsits integer value and stores that as a
double. Effects:setValue(QVariant(3.14))→ stores3.0(fractional part lost).setValue(QVariant(NaN))→ stores0.0(toInt()returns 0).setValue(QVariant(1.5e15))→ silently clamped to int range.Anywhere DLT messages are constructed programmatically with floating-
point arguments via this overload, the wire output is wrong.
Fix:
value.toInt()→value.toDouble(). One-character change.2.
QDltSegmentedMsg::add—sequence * chunkSizeoverflowqdlt/qdltsegmentedmsg.cpp:141–154:Both
sequence(chunk segment) andchunkSize(start segment) comefrom the wire. The check
sequence < chunksonly validates thechunk index; the multiplication
sequence * chunkSizeis performedin
uint32_tand can wrap. With a crafted start segment declaring alarge
chunkSizeand a chunk-segment message with a small butnon-zero
sequence, the product wraps to a value smaller thanpayload.size(), sopayload.replace()succeeds but writes thechunk into the wrong region of the buffer.
Fix: compute the offset in
quint64so the multiplication can'twrap, then reject any chunk whose end (
chunk_offset + chunkSize)would extend past the resized payload size before calling
replace().Verification
not cover the cases above.
payloadisresized to the start-segment-declared size atline 112, which the new bound-check uses as the upper limit.
intfor thereplace()call is safe after thebound check has guaranteed the offset fits.
Notes
qdlt/tests/-style coverage ifmaintainers point me at the right harness shape.
mid()calls inqdltargument.cpp:174,178and
qdltimporter.cpp:942are real but milder (Qt'smid()truncates gracefully rather than reading OOB), and I'll send
those as a separate PR rather than bundle here.