Skip to content

Commit 5aba430

Browse files
committed
Add docs; minor condition change to ensure logarithmic time in corner case
1 parent 7691d06 commit 5aba430

File tree

1 file changed

+13
-9
lines changed

1 file changed

+13
-9
lines changed

libc/src/__support/freetrie.h

Lines changed: 13 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -151,13 +151,13 @@ LIBC_INLINE FreeTrie::Node *FreeTrie::find_best_fit(size_t size) {
151151
Node *deferred_upper_trie = nullptr;
152152
FreeTrie::SizeRange deferred_upper_range{0, 0};
153153

154-
// Inductively assume all better fits than the current best are in the
155-
// current subtrie.
156154
while (true) {
157155
LIBC_ASSERT(cur_range.contains(cur->size()) &&
158156
"trie node size out of range");
159157
LIBC_ASSERT(cur_range.max() >= size &&
160158
"range could not fit requested size");
159+
LIBC_ASSERT((!best_fit || cur_range.min < best_fit->size()) &&
160+
"range could not contain a best fit");
161161

162162
// If the current node is an exact fit, it is a best fit.
163163
if (cur->size() == size)
@@ -168,19 +168,23 @@ LIBC_INLINE FreeTrie::Node *FreeTrie::find_best_fit(size_t size) {
168168
best_fit = cur;
169169

170170
// If there is a deferred upper subtrie, then the current node is
171-
// somewhere in its lower sibiling subtire. That means that the new best
171+
// somewhere in its lower sibling subtrie. That means that the new best
172172
// fit is better than the best fit in the deferred subtrie.
173173
LIBC_ASSERT(
174174
!deferred_upper_trie ||
175-
deferred_upper_range.min > cur->size() &&
175+
deferred_upper_range.min > best_fit->size() &&
176176
"deferred upper subtrie should be outclassed by new best fit");
177177
deferred_upper_trie = nullptr;
178178
}
179179

180-
// Determine which subtries might contain better fits.
180+
// Determine which subtries might contain the best fit.
181181
bool lower_impossible = !cur->lower || cur_range.lower().max() < size;
182182
bool upper_impossible =
183-
!cur->upper || (best_fit && cur_range.upper().min >= best_fit->size());
183+
!cur->upper ||
184+
// If every node in the lower trie fits
185+
(!lower_impossible && cur_range.min >= size) ||
186+
// If every node in the upper trie is worse than the current best
187+
(best_fit && cur_range.upper().min >= best_fit->size());
184188

185189
if (lower_impossible && upper_impossible) {
186190
if (!deferred_upper_trie)
@@ -189,8 +193,7 @@ LIBC_INLINE FreeTrie::Node *FreeTrie::find_best_fit(size_t size) {
189193
// provides a better fit.
190194
//
191195
// This can only ever be reached once. In a deferred upper subtrie, every
192-
// node fits, so the scan can always summarily ignore an upper suptrie
193-
// rather than deferring it.
196+
// node fits, so the higher of two subtries can never contain a best fit.
194197
cur = deferred_upper_trie;
195198
cur_range = deferred_upper_range;
196199
deferred_upper_trie = nullptr;
@@ -206,7 +209,8 @@ LIBC_INLINE FreeTrie::Node *FreeTrie::find_best_fit(size_t size) {
206209
} else {
207210
// Both subtries might contain a better fit. Any fit in the lower subtrie
208211
// is better than the any fit in the upper subtrie, so scan the lower
209-
// subtrie and return to the upper one if necessary.
212+
// and return to the upper only if no better fits were found. (Any better
213+
// fit found clears the deferred upper subtrie.)
210214
LIBC_ASSERT(!deferred_upper_trie ||
211215
cur_range.upper().max() < deferred_upper_range.min &&
212216
"old deferred upper subtrie should be outclassed by new");

0 commit comments

Comments
 (0)