gbranden pushed a commit to branch master
in repository groff.
commit 95b6901bb47ae10d41592b125e90816fe3412ad1
Author: G. Branden Robinson <[email protected]>
AuthorDate: Wed Jun 24 19:12:58 2026 -0500
[troff]: Add overflow check to `dictionary` type.
* src/roff/troff/dictionary.cpp: Preprocessor-include "errarg.h" and
"error.h" to make visible `fatal()` function.
(dictionary::lookup): Add overflow check of dictionary capacity.
GCC's static analyzer was suspicious that it could overflow.
`capacity` is a `ssize_t`, but C++'s allocator (behind `new`) uses
`size_t`. If `capacity` wraps (overflows), emit fatal error.
---
ChangeLog | 10 ++++++++++
src/roff/troff/dictionary.cpp | 7 +++++++
2 files changed, 17 insertions(+)
diff --git a/ChangeLog b/ChangeLog
index 229ab8564..e3d80c9c5 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,13 @@
+2026-06-24 G. Branden Robinson <[email protected]>
+
+ * src/roff/troff/dictionary.cpp: Preprocessor-include "errarg.h"
+ and "error.h" to make visible `fatal()` function.
+ (dictionary::lookup): Add overflow check of dictionary capacity.
+ GCC's static analyzer was suspicious that it could overflow.
+ `capacity` is a `ssize_t`, but C++'s allocator (behind `new`)
+ uses `size_t`. If `capacity` wraps (overflows), emit fatal
+ error.
+
2026-06-24 G. Branden Robinson <[email protected]>
[libgroff,troff]: Reallocate fatal error exit responsibilities,
diff --git a/src/roff/troff/dictionary.cpp b/src/roff/troff/dictionary.cpp
index 8cdcc62b2..9418583a2 100644
--- a/src/roff/troff/dictionary.cpp
+++ b/src/roff/troff/dictionary.cpp
@@ -30,6 +30,8 @@ along with this program. If not, see
<http://www.gnu.org/licenses/>. */
// libgroff
#include "symbol.h" // prerequisite of dictionary.h
#include "dictionary.h"
+#include "errarg.h" // prerequisite of error.h
+#include "error.h" // prerequisite of error.h
// is 'p' a good size for a hash table
@@ -81,6 +83,11 @@ void *dictionary::lookup(symbol s, void *v)
capacity = ssize_t(capacity * factor);
while (!is_good_size(capacity))
++capacity;
+ if (capacity < 0)
+ // If `capacity` wrapped, the old size must have fit in a signed
+ // integer.
+ fatal("cannot grow dictionary beyond %1 entries",
+ static_cast<int>(old_capacity));
association *old_table = table;
table = new association[capacity];
occupancy = 0;
_______________________________________________
groff-commit mailing list
[email protected]
https://lists.gnu.org/mailman/listinfo/groff-commit