Repository navigation
Conversation
|
A more refactored version was committed as r39800. Thank you for contributing to Nmap. |
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.
[NSE] iec61850mms.lua: fix infinite loop on malformed TPKT length
What
MMSDecoder:unpackmmsFromTPKT()innselib/iec61850mms.luawalks the TPKT segmentsof an MMS response with a loop that advances by
TPKT_pos = TPKT_pos + TPKT_len, whereTPKT_lenis the 16-bit length field taken directly from the response. The loop onlyends when it sees a COTP TPDU byte equal to
0x80.If a target returns a segment whose TPKT length field is
0(and whose COTP TPDUbyte is not
0x80),TPKT_posnever advances, the same bytes are re-read everyiteration, and the loop spins forever. There is also no check that the buffer actually
contains the TPKT+COTP headers being unpacked.
Why it matters
unpackmmsFromTPKTis reached fromscripts/iec61850-mms.nse, which callsdecoder:unpackAndDecode(recv)on data received from the target (an IEC 61850 / MMSdevice on TCP 102) with no surrounding
pcall. A malicious or compromised device cantherefore hang the script. Because the loop is pure CPU with no I/O /
yield, NSE'scooperative scheduler has no point at which to regain control, so the hang can stall the
whole
--scriptphase rather than just the one host. This is low-level severity inreach (only the
iec61850-mmsscript) but the impact — a remotely triggered hang — isworse than a clean error.
Fix
Two guards in the loop:
headers, so a truncated response can't read past the end of the string.
TPKT_lentoo small to move past theheader (
< 7), which is exactly the case that failed to make progress.Well-formed single- and multi-segment responses parse exactly as before; the malformed
zero-length segment is now rejected (returns
nil, consistent with the function's othererror paths) instead of looping forever.
Reproduction
Parsing a single TPKT+COTP segment with bytes
03 00 00 00 02 f0 00 …(TPKT length = 0,COTP TPDU =
0x00) loops forever before this change and returnsnilafter it. Awell-formed segment (
03 00 00 08 02 f0 80 …) and valid multi-segment responses areunaffected.
Note
The same file has several
while (newpos < pos + elen)TLV-parsing loops (around lines~230–630) that are worth a look for the same "sub-element fails to advance" class of
non-termination; this PR addresses the TPKT loop specifically.
Reporter
Ibrahim Maqtoush (@Zasnit1)