Skip to content

CFRunLoop: search the sources array with its own count when removing invalidated sources#63

Open
DTW-Thalion wants to merge 1 commit into
gnustep:masterfrom
DTW-Thalion:fix/cfrunloop-source-remove
Open

CFRunLoop: search the sources array with its own count when removing invalidated sources#63
DTW-Thalion wants to merge 1 commit into
gnustep:masterfrom
DTW-Thalion:fix/cfrunloop-source-remove

Conversation

@DTW-Thalion

Copy link
Copy Markdown
Contributor

Summary

CFRunLoopSourceRemoveInvalidated searched the sources0 array using the
count of the timers array:

CFIndex idx = CFArrayGetFirstIndexOfValue(ctxt->sources0,
                                          CFRangeMake(0, CFArrayGetCount(ctxt->timers)),
                                          (CFRunLoopSourceRef) source);

With no timers registered the search range was (0, 0), so an invalidated
version-0 source was never found and never removed from the run loop (it also
stayed in sources0set, so CFRunLoopContainsSource kept returning true). When
there were more timers than sources, the range ran past the end of the
sources0 array.

Fix

Use CFArrayGetCount(ctxt->sources0), matching the timer-removal path
(CFRunLoopTimerRemoveInvalidated).

Test

Tests/CFRunLoop/source_invalidate.m: add a version-0 source (no timers),
invalidate it, and confirm CFRunLoopContainsSource returns false.

@HendrikHuebner HendrikHuebner left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

Comment thread Tests/CFRunLoop/source_invalidate.m Outdated

/* CFRunLoopSourceRemoveInvalidated searched the sources0 array using the
* count of the timers array, so with no timers the search range was (0, 0)
* and an invalidated source was never removed from the run loop. */

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Remove the comment

CFRunLoopSourceRemoveInvalidated searched ctxt->sources0 using the count
of ctxt->timers.  With no timers the search range was (0, 0), so an
invalidated version-0 source was never found and never removed from the
run loop; with more timers than sources the range ran past the end of
the sources array.

Use CFArrayGetCount(ctxt->sources0), matching the timer path.

Add Tests/CFRunLoop/source_invalidate.m.
@DTW-Thalion DTW-Thalion force-pushed the fix/cfrunloop-source-remove branch from c3f9cc7 to 24f394f Compare July 3, 2026 14:17
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Development

Successfully merging this pull request may close these issues.

2 participants