Recent NSTimer -> CFTimerRunLoopRef change is unstable in general browsing. This is Deployment mode through Safari on 10.4.3. Crash as follows, every time: Exception: EXC_BAD_ACCESS (0x0001) Codes: KERN_PROTECTION_FAILURE (0x0002) at 0x00000000 Thread 0 Crashed: 0 com.apple.CoreFoundation 0x907400bc CFArrayGetCount + 52 1 com.apple.WebCore 0x00456f3c sendDeferredTimerEvents(__CFRunLoopTimer*, void*) + 64 (icplusplus.c:28) 2 com.apple.CoreFoundation 0x90770ae0 __CFRunLoopDoTimer + 184 3 com.apple.CoreFoundation 0x9075d458 __CFRunLoopRun + 1680 4 com.apple.CoreFoundation 0x9075ca0c CFRunLoopRunSpecific + 268 5 com.apple.HIToolbox 0x931831e0 RunCurrentEventLoopInMode + 264 6 com.apple.HIToolbox 0x93182874 ReceiveNextEventCommon + 380 7 com.apple.HIToolbox 0x931826e0 BlockUntilNextEventMatchingListInMode + 96 8 com.apple.AppKit 0x93681904 _DPSNextEvent + 384 9 com.apple.AppKit 0x936815c8 -[NSApplication nextEventMatchingMask:untilDate:inMode:dequeue:] + 116 10 com.apple.SafariDev 0x00006ef0 0x1000 + 24304 11 com.apple.AppKit 0x9367db0c -[NSApplication run] + 472 12 com.apple.AppKit 0x9376e618 NSApplicationMain + 452 13 com.apple.SafariDev 0x0000265c 0x1000 + 5724 14 com.apple.SafariDev 0x00056d1c 0x1000 + 351516
Confirmed w/Nov 8 nightly.
I guess I can just roll it out -- or if there was a reliable way to reproduce I could fix it quickly!
Mitz said the steps to reproduce are: "just go to any form, click in one text field, wait, click in another. http://bugzilla.opendarwin.org/query.cgi will do".
This is the errant function: WebCore/kwq/KWQObject.mm:250 static void sendDeferredTimerEvents(CFRunLoopTimerRef, void *) { CFRelease(sendDeferredTimerEventsTimer); sendDeferredTimerEventsTimer = 0; CFArrayRef timers = deferredTimers; deferredTimers = 0; CFArrayApplyFunction(timers, CFRangeMake(0, CFArrayGetCount(timers)), sendDeferredTimerEvent, 0); CFRelease(timers); } GDB says deferredTimers is null (probably never initialized). I notice that other parts of the code, like timerFired, check for a null deferredTimers -- maybe we should do the same here? If so, I'd suggest making a static getDeferredTimers() accessor method to do the work in one place.
s/deferredTimers/timers/ *timers* is null, probably because deferredTimers was never initialized.
I checked in nil check for timers in sendDeferredTimerEvents.