diff options
author | Nick Mathewson <nickm@torproject.org> | 2016-02-17 14:19:47 -0500 |
---|---|---|
committer | Nick Mathewson <nickm@torproject.org> | 2016-02-23 07:31:58 -0500 |
commit | 21f72990dbd2fb1fa98261a39544771a43ee422a (patch) | |
tree | fab897fa48a7de24f18946ff53e4997f260bf6e7 /src/common/container.c | |
parent | 549493846782efa7d6655317844782b6acade1b2 (diff) | |
download | tor-21f72990dbd2fb1fa98261a39544771a43ee422a.tar.gz tor-21f72990dbd2fb1fa98261a39544771a43ee422a.zip |
Simple fix for integer overflow in smartlist_heapify.
Diffstat (limited to 'src/common/container.c')
-rw-r--r-- | src/common/container.c | 22 |
1 files changed, 19 insertions, 3 deletions
diff --git a/src/common/container.c b/src/common/container.c index 2e42c9ee07..1de8e7ded4 100644 --- a/src/common/container.c +++ b/src/common/container.c @@ -840,9 +840,17 @@ smartlist_sort_pointers(smartlist_t *sl) * * For a 1-indexed array, we would use LEFT_CHILD[x] = 2*x and RIGHT_CHILD[x] * = 2*x + 1. But this is C, so we have to adjust a little. */ -//#define LEFT_CHILD(i) ( ((i)+1)*2 - 1) -//#define RIGHT_CHILD(i) ( ((i)+1)*2 ) -//#define PARENT(i) ( ((i)+1)/2 - 1) + +/* MAX_PARENT_IDX is the largest IDX in the smartlist which might have + * children whose indices fit inside an int. + * LEFT_CHILD(MAX_PARENT_IDX) == INT_MAX-2; + * RIGHT_CHILD(MAX_PARENT_IDX) == INT_MAX-1; + * LEFT_CHILD(MAX_PARENT_IDX + 1) == INT_MAX // impossible, see max list size. + */ +#define MAX_PARENT_IDX ((INT_MAX - 2) / 2) +/* If this is true, then i is small enough to potentially have children + * in the smartlist, and it is save to use LEFT_CHILD/RIGHT_CHILD on it. */ +#define IDX_MAY_HAVE_CHILDREN(i) ((i) <= MAX_PARENT_IDX) #define LEFT_CHILD(i) ( 2*(i) + 1 ) #define RIGHT_CHILD(i) ( 2*(i) + 2 ) #define PARENT(i) ( ((i)-1) / 2 ) @@ -876,6 +884,14 @@ smartlist_heapify(smartlist_t *sl, int idx) { while (1) { + if (! IDX_MAY_HAVE_CHILDREN(idx)) { + /* idx is so large that it cannot have any children, since doing so + * would mean the smartlist was over-capacity. Therefore it cannot + * violate the heap property by being greater than a child (since it + * doesn't have any). */ + return; + } + int left_idx = LEFT_CHILD(idx); int best_idx; |