@@ -618,8 +618,9 @@ function Session:update_threads(cb)
618618 for _ , thread in pairs (response .threads ) do
619619 threads [thread .id ] = thread
620620 local old_thread = self .threads [thread .id ]
621- if old_thread and old_thread .stopped then
622- thread .stopped = true
621+ if old_thread then
622+ thread .stopped = old_thread .stopped
623+ thread .frames = old_thread .frames
623624 end
624625 end
625626 self .threads = threads
@@ -646,61 +647,61 @@ end
646647
647648--- @param stopped dap.StoppedEvent
648649function Session :event_stopped (stopped )
649- if self .dirty .threads or (stopped .threadId and self .threads [stopped .threadId ] == nil ) then
650- self :update_threads (function (err )
650+ coroutine.wrap (function ()
651+ local co = coroutine.running ()
652+
653+ if self .dirty .threads or (stopped .threadId and self .threads [stopped .threadId ] == nil ) then
654+ self :update_threads (co_resume (co ))
655+ local err = coroutine.yield ()
651656 if err then
652657 utils .notify (' Error retrieving threads: ' .. utils .fmt_error (err ), vim .log .levels .ERROR )
653658 return
654659 end
655- self :event_stopped (stopped )
656- end )
657- return
658- end
660+ end
659661
660- local should_jump = stopped .reason ~= ' pause' or stopped .allThreadsStopped
661-
662- -- Some debug adapters allow to continue/step via custom REPL commands (via evaluate)
663- -- That by-passes `clear_running`, resulting in self.stopped_thread_id still being set
664- -- Dont auto-continue if`threadId == self.stopped_thread_id`, but stop & jump
665- if self .stopped_thread_id and self .stopped_thread_id ~= stopped .threadId and should_jump then
666- if defaults (self ).auto_continue_if_many_stopped then
667- local thread = self .threads [self .stopped_thread_id ]
668- local thread_name = thread and thread .name or self .stopped_thread_id
669- log .debug (
670- ' Received stopped event, but ' .. thread_name .. ' is already stopped. ' ..
671- ' Resuming newly stopped thread. ' ..
672- ' To disable this set the `auto_continue_if_many_stopped` option to false.' )
673- self :request (' continue' , { threadId = stopped .threadId })
674- return
675- else
676- -- Allow thread to stop, but don't jump to it because stepping
677- -- interleaved between threads is confusing
678- should_jump = false
662+ local should_jump = stopped .reason ~= ' pause' or stopped .allThreadsStopped
663+
664+ -- Some debug adapters allow to continue/step via custom REPL commands (via evaluate)
665+ -- That by-passes `clear_running`, resulting in self.stopped_thread_id still being set
666+ -- Dont auto-continue if`threadId == self.stopped_thread_id`, but stop & jump
667+ if self .stopped_thread_id and self .stopped_thread_id ~= stopped .threadId and should_jump then
668+ if defaults (self ).auto_continue_if_many_stopped then
669+ local thread = self .threads [self .stopped_thread_id ]
670+ local thread_name = thread and thread .name or self .stopped_thread_id
671+ log .debug (
672+ ' Received stopped event, but ' .. thread_name .. ' is already stopped. ' ..
673+ ' Resuming newly stopped thread. ' ..
674+ ' To disable this set the `auto_continue_if_many_stopped` option to false.' )
675+ self :request (' continue' , { threadId = stopped .threadId }, function () end )
676+ return
677+ else
678+ -- Allow thread to stop, but don't jump to it because stepping
679+ -- interleaved between threads is confusing
680+ should_jump = false
681+ end
682+ end
683+ if should_jump then
684+ self .stopped_thread_id = stopped .threadId
679685 end
680- end
681- if should_jump then
682- self .stopped_thread_id = stopped .threadId
683- end
684686
685- if stopped .allThreadsStopped then
686- progress .report (' All threads stopped' )
687- for _ , thread in pairs (self .threads ) do
688- thread .stopped = true
687+ if stopped .allThreadsStopped then
688+ progress .report (' All threads stopped' )
689+ for _ , thread in pairs (self .threads ) do
690+ thread .stopped = true
691+ end
692+ elseif stopped .threadId then
693+ progress .report (' Thread stopped: ' .. stopped .threadId )
694+ self .threads [stopped .threadId ].stopped = true
695+ else
696+ utils .notify (' Stopped event received, but no threadId or allThreadsStopped' , vim .log .levels .WARN )
689697 end
690- elseif stopped .threadId then
691- progress .report (' Thread stopped: ' .. stopped .threadId )
692- self .threads [stopped .threadId ].stopped = true
693- else
694- utils .notify (' Stopped event received, but no threadId or allThreadsStopped' , vim .log .levels .WARN )
695- end
696698
697- if not stopped .threadId then
698- return
699- end
700- local thread = self .threads [stopped .threadId ]
701- assert (thread , ' Thread not found: ' .. stopped .threadId )
699+ if not stopped .threadId then
700+ return
701+ end
702+ local thread = self .threads [stopped .threadId ]
703+ assert (thread , ' Thread not found: ' .. stopped .threadId )
702704
703- coroutine.wrap (function ()
704705 local err , response = self :request (' stackTrace' , { threadId = stopped .threadId ; })
705706 if err then
706707 utils .notify (' Error retrieving stack traces: ' .. utils .fmt_error (err ), vim .log .levels .ERROR )
0 commit comments