Index: source/Plugins/OperatingSystem/Python/OperatingSystemPython.cpp =================================================================== --- source/Plugins/OperatingSystem/Python/OperatingSystemPython.cpp +++ source/Plugins/OperatingSystem/Python/OperatingSystemPython.cpp @@ -156,9 +156,10 @@ Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_OS)); - // First thing we have to do is to try to get the API lock, and the run lock. - // We're going to change the thread content of the process, and we're going - // to use python, which requires the API lock to do it. + // First thing we have to do is to try to get the API lock, and the + // interpreter lock. We're going to change the thread content of the process, + // and we're going to use python, which requires the API lock to do it. We + // need the interpreter lock to make sure thread_info_dict stays alive. // // If someone already has the API lock, that is ok, we just want to avoid // external code from making new API calls while this call is happening. @@ -166,9 +167,10 @@ // This is a recursive lock so we can grant it to any Python code called on // the stack below us. Target &target = m_process->GetTarget(); - std::unique_lock lock(target.GetAPIMutex(), - std::defer_lock); - lock.try_lock(); + std::unique_lock api_lock(target.GetAPIMutex(), + std::defer_lock); + api_lock.try_lock(); + auto interpreter_lock = m_interpreter->AcquireInterpreterLock(); if (log) log->Printf("OperatingSystemPython::UpdateThreadList() fetching thread " @@ -176,12 +178,8 @@ m_process->GetID()); // The threads that are in "new_thread_list" upon entry are the threads from - // the - // lldb_private::Process subclass, no memory threads will be in this list. - - auto interpreter_lock = - m_interpreter - ->AcquireInterpreterLock(); // to make sure threads_list stays alive + // the lldb_private::Process subclass, no memory threads will be in this + // list. StructuredData::ArraySP threads_list = m_interpreter->OSPlugin_ThreadsInfo(m_python_object_sp); @@ -301,20 +299,24 @@ if (!IsOperatingSystemPluginThread(thread->shared_from_this())) return reg_ctx_sp; - // First thing we have to do is get the API lock, and the run lock. We're - // going to change the thread - // content of the process, and we're going to use python, which requires the - // API lock to do it. - // So get & hold that. This is a recursive lock so we can grant it to any - // Python code called on the stack below us. + // First thing we have to do is to try to get the API lock, and the + // interpreter lock. We're going to change the thread content of the process, + // and we're going to use python, which requires the API lock to do it. We + // need the interpreter lock to make sure thread_info_dict stays alive. + // + // If someone already has the API lock, that is ok, we just want to avoid + // external code from making new API calls while this call is happening. + // + // This is a recursive lock so we can grant it to any Python code called on + // the stack below us. Target &target = m_process->GetTarget(); - std::lock_guard guard(target.GetAPIMutex()); + std::unique_lock api_lock(target.GetAPIMutex(), + std::defer_lock); + api_lock.try_lock(); + auto interpreter_lock = m_interpreter->AcquireInterpreterLock(); Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_THREAD)); - auto lock = - m_interpreter - ->AcquireInterpreterLock(); // to make sure python objects stays alive if (reg_data_addr != LLDB_INVALID_ADDRESS) { // The registers data is in contiguous memory, just create the register // context using the address provided @@ -383,18 +385,21 @@ tid, context); if (m_interpreter && m_python_object_sp) { - // First thing we have to do is get the API lock, and the run lock. We're - // going to change the thread - // content of the process, and we're going to use python, which requires the - // API lock to do it. - // So get & hold that. This is a recursive lock so we can grant it to any - // Python code called on the stack below us. + // First thing we have to do is to try to get the API lock, and the + // interpreter lock. We're going to change the thread content of the + // process, and we're going to use python, which requires the API lock to + // do it. We need the interpreter lock to make sure thread_info_dict stays + // alive. + // + // If someone already has the API lock, that is ok, we just want to avoid + // external code from making new API calls while this call is happening. + // + // This is a recursive lock so we can grant it to any Python code called on + // the stack below us. Target &target = m_process->GetTarget(); std::lock_guard guard(target.GetAPIMutex()); + auto interpreter_lock = m_interpreter->AcquireInterpreterLock(); - auto lock = m_interpreter->AcquireInterpreterLock(); // to make sure - // thread_info_dict - // stays alive StructuredData::DictionarySP thread_info_dict = m_interpreter->OSPlugin_CreateThread(m_python_object_sp, tid, context); std::vector core_used_map;