diff options
author | Mark Mielke <mark.mielke@gmail.com> | 2020-06-20 06:15:39 -0400 |
---|---|---|
committer | Mark Mielke <mark.mielke@gmail.com> | 2020-07-07 04:29:26 -0400 |
commit | 7932f5e483f790169a0d2da2a7cc73c76ca93817 (patch) | |
tree | 5029a853bb170935858f5a8592cae04712c16449 | |
parent | 38726ce083db1a9227325bf87989513499bfa698 (diff) | |
download | tigervnc-7932f5e483f790169a0d2da2a7cc73c76ca93817.tar.gz tigervnc-7932f5e483f790169a0d2da2a7cc73c76ca93817.zip |
Fix division by zero exception in SSecurityPlain.
If using SSecurityPlain and the user specifies an empty username
and password, it will invoke InStream::checkNoWait(0) which will
cause a division by zero when calculating the number of available
items.
Enhance InStream::check() to behave properly when asked for
zero items, or zero sized items.
Add comments to InStream::check(), InStream::checkNoWait(),
and InStream::readBytes() to document expected behaviour
when requested to check or read zero items, or an item with
zero size.
-rw-r--r-- | common/rdr/InStream.h | 13 |
1 files changed, 11 insertions, 2 deletions
diff --git a/common/rdr/InStream.h b/common/rdr/InStream.h index f71a4d9e..a8e515da 100644 --- a/common/rdr/InStream.h +++ b/common/rdr/InStream.h @@ -39,15 +39,19 @@ namespace rdr { // itemSize bytes. Returns the number of items in the buffer (up to a // maximum of nItems). If wait is false, then instead of blocking to wait // for the bytes, zero is returned if the bytes are not immediately - // available. + // available. If itemSize or nItems is zero, check() will return zero. inline size_t check(size_t itemSize, size_t nItems=1, bool wait=true) { size_t nAvail; + if (itemSize == 0 || nItems == 0) + return 0; + if (itemSize > (size_t)(end - ptr)) return overrun(itemSize, nItems, wait); + // itemSize cannot be zero at this point nAvail = (end - ptr) / itemSize; if (nAvail < nItems) return nAvail; @@ -58,8 +62,12 @@ namespace rdr { // checkNoWait() tries to make sure that the given number of bytes can // be read without blocking. It returns true if this is the case, false // otherwise. The length must be "small" (less than the buffer size). + // If length is zero, checkNoWait() will return true. - inline bool checkNoWait(size_t length) { return check(length, 1, false)!=0; } + inline bool checkNoWait(size_t length) + { + return length == 0 || check(length, 1, false) > 0; + } // readU/SN() methods read unsigned and signed N-bit integers. @@ -94,6 +102,7 @@ namespace rdr { } // readBytes() reads an exact number of bytes. + // If length is zero, readBytes() will return immediately. void readBytes(void* data, size_t length) { while (length > 0) { |