Eliot Miranda uploaded a new version of Tools to project The Trunk:
http://source.squeak.org/trunk/Tools-eem.258.mcz ==================== Summary ==================== Name: Tools-eem.258 Author: eem Time: 14 August 2010, 6:45:20.412 pm UUID: 261ba269-1565-45b1-9f7b-b6ce8cee312c Ancestors: Tools-eem.257 Don't cache the debugger's debuggerMap, its not safe. Add preference for and support of opening a debugger for an error in a background process when the UI process is busy. =============== Diff against Tools-eem.257 =============== Item was added: + ----- Method: Debugger class>>interruptUIProcessIfBlockedOnErrorInBackgroundProcess: (in category 'preferences') ----- + interruptUIProcessIfBlockedOnErrorInBackgroundProcess: aBoolean + InterruptUIProcessIfBlockedOnErrorInBackgroundProcess := aBoolean! Item was changed: CodeHolder subclass: #Debugger + instanceVariableNames: 'interruptedProcess interruptedController contextStack contextStackTop contextStackIndex contextStackList receiverInspector contextVariablesInspector externalInterrupt proceedValue selectingPC savedCursor isolationHead failedProject errorWasInUIProcess labelString message' + classVariableNames: 'ContextStackKeystrokes ErrorRecursion InterruptUIProcessIfBlockedOnErrorInBackgroundProcess' - instanceVariableNames: 'interruptedProcess interruptedController contextStack contextStackTop contextStackIndex contextStackList receiverInspector contextVariablesInspector externalInterrupt proceedValue selectingPC debuggerMap savedCursor errorWasInUIProcess labelString message' - classVariableNames: 'ContextStackKeystrokes ErrorRecursion' poolDictionaries: '' category: 'Tools-Debugger'! !Debugger commentStamp: '<historical>' prior: 0! I represent the machine state at the time of an interrupted process. I also represent a query path into the state of the process. The debugger is typically viewed through a window that views the stack of suspended contexts, the code for, and execution point in, the currently selected message, and inspectors on both the receiver of the currently selected message, and the variables in the current context. Special note on recursive errors: Some errors affect Squeak's ability to present a debugger. This is normally an unrecoverable situation. However, if such an error occurs in an isolation layer, Squeak will attempt to exit from the isolation layer and then present a debugger. Here is the chain of events in such a recovery. * A recursive error is detected. * The current project is queried for an isolationHead * Changes in the isolationHead are revoked * The parent project of isolated project is returned to * The debugger is opened there and execution resumes. If the user closes that debugger, execution continues in the outer project and layer. If, after repairing some damage, the user proceeds from the debugger, then the isolationHead is re-invoked, the failed project is re-entered, and execution resumes in that world. ! Item was added: + ----- Method: Debugger class>>ifPreferredInterruptUIProcessIfBlocked: (in category 'private') ----- + ifPreferredInterruptUIProcessIfBlocked: errorWasInUIProcess + | sema | + errorWasInUIProcess ifTrue: + [^self]. + self interruptUIProcessIfBlockedOnErrorInBackgroundProcess ifFalse: + [^self]. + "Only interrupt the UI if it is unresponsive (and so is doing something that needs + interrupting). Test using addDeferredUIMessage: to see if it is running UI activities." + sema := Semaphore new. + Project current addDeferredUIMessage: [sema signal]. + (sema waitTimeoutMSecs: 100) ifTrue: + [[Project current interruptName: 'Interrupt from Background Error'] fork] + + "| s | + s := Semaphore new. + [self assert: 0 > 1000. s signal] fork. + s wait"! Item was changed: ----- Method: Debugger class>>openOn:context:label:contents:fullView: (in category 'opening') ----- openOn: process context: context label: title contents: contentsStringOrNil fullView: bool "Open a notifier in response to an error, halt, or notify. A notifier view just shows a short view of the sender stack and provides a menu that lets the user open a full debugger." + | controller errorWasInUIProcess block | - | controller errorWasInUIProcess | Smalltalk isMorphic ifTrue: [errorWasInUIProcess := Project spawnNewProcessIfThisIsUI: process] ifFalse: [controller := ScheduledControllers activeControllerProcess == process ifTrue: [ScheduledControllers activeController]]. + block := [ - WorldState addDeferredUIMessage: [ [ | debugger | debugger := self new process: process controller: controller context: context. Smalltalk isMorphic ifTrue: ["schedule debugger in deferred UI message to address redraw problems after opening a debugger e.g. from the testrunner." "WorldState addDeferredUIMessage: ["bool ifTrue: [debugger openFullNoSuspendLabel: title] ifFalse: [debugger openNotifierContents: contentsStringOrNil label: title]] ifFalse: ["deferred UI message would require special controller in MVC" bool ifTrue: [debugger openFullNoSuspendLabel: title] ifFalse: [debugger openNotifierContents: contentsStringOrNil label: title]]. debugger errorWasInUIProcess: errorWasInUIProcess. Preferences logDebuggerStackToFile ifTrue: [ Smalltalk logError: title inContext: context to: 'SqueakDebug.log']. Smalltalk isMorphic ifFalse: [ScheduledControllers searchForActiveController "needed since openNoTerminate (see debugger #open...) does not set up activeControllerProcess if activeProcess (this fork) is not the current activeControllerProcess (see #scheduled:from:)"]. ] on: Error do: [:ex | self primitiveError: 'Orginal error: ', title asString, '. Debugger error: ', ([ex description] on: Error do: ['a ', ex class printString]), ':' ] ]. + self ifPreferredInterruptUIProcessIfBlocked: errorWasInUIProcess. + Project current addDeferredUIMessage: block. + process suspend! - process suspend. - ! Item was changed: ----- Method: Debugger>>debuggerMap (in category 'accessing') ----- debuggerMap + ^self selectedContext debuggerMap! - ^debuggerMap ifNil: - [debuggerMap := self selectedContext debuggerMap].! Item was added: + ----- Method: Debugger class>>interruptUIProcessIfBlockedOnErrorInBackgroundProcess (in category 'preferences') ----- + interruptUIProcessIfBlockedOnErrorInBackgroundProcess + <preference: 'Interrupt UI process on background error' + category: 'debug' + description: 'When enabled, the debugger will interrupt the UI process if an error occurs in a background process and the UI process is blocked.' + type: #Boolean> + ^InterruptUIProcessIfBlockedOnErrorInBackgroundProcess ifNil: [false]! |
Free forum by Nabble | Edit this page |