https://github.com/da-viper updated https://github.com/llvm/llvm-project/pull/208471
>From ca792bf4a256048f6912d940a131b162b887f971 Mon Sep 17 00:00:00 2001 From: Ebuka Ezike <[email protected]> Date: Thu, 9 Jul 2026 15:03:29 +0100 Subject: [PATCH] [lldb-dap] Avoid data race when clearing an OptionValue The clear function guarded by the internal mutex. This happens when we have to threads one trying to set a value and the other reseting the value. --- lldb/include/lldb/Interpreter/OptionValue.h | 4 ++-- lldb/include/lldb/Interpreter/OptionValueArch.h | 2 ++ lldb/include/lldb/Interpreter/OptionValueArray.h | 1 + lldb/include/lldb/Interpreter/OptionValueBoolean.h | 1 + lldb/include/lldb/Interpreter/OptionValueChar.h | 1 + lldb/include/lldb/Interpreter/OptionValueDictionary.h | 1 + lldb/include/lldb/Interpreter/OptionValueEnumeration.h | 1 + lldb/include/lldb/Interpreter/OptionValueFileColonLine.h | 1 + lldb/include/lldb/Interpreter/OptionValueFileSpec.h | 1 + lldb/include/lldb/Interpreter/OptionValueFormat.h | 1 + lldb/include/lldb/Interpreter/OptionValueLanguage.h | 1 + lldb/include/lldb/Interpreter/OptionValuePathMappings.h | 1 + lldb/include/lldb/Interpreter/OptionValueRegex.h | 1 + lldb/include/lldb/Interpreter/OptionValueSInt64.h | 1 + lldb/include/lldb/Interpreter/OptionValueString.h | 1 + lldb/include/lldb/Interpreter/OptionValueUInt64.h | 1 + lldb/include/lldb/Interpreter/OptionValueUUID.h | 1 + lldb/source/Interpreter/OptionValueFormatEntity.cpp | 1 + lldb/source/Interpreter/OptionValueProperties.cpp | 1 + 19 files changed, 21 insertions(+), 2 deletions(-) diff --git a/lldb/include/lldb/Interpreter/OptionValue.h b/lldb/include/lldb/Interpreter/OptionValue.h index 193f2e44aca1b..e364fc0817754 100644 --- a/lldb/include/lldb/Interpreter/OptionValue.h +++ b/lldb/include/lldb/Interpreter/OptionValue.h @@ -372,6 +372,8 @@ class OptionValue { // set from the command line or as a setting, // versus if we just have the default value that // was already populated in the option value. + mutable std::recursive_mutex m_mutex; + private: std::optional<ArchSpec> GetArchSpecValue() const; bool SetArchSpecValue(ArchSpec arch_spec); @@ -412,8 +414,6 @@ class OptionValue { bool SetFormatEntityValue(const FormatEntity::Entry &entry); const RegularExpression *GetRegexValue() const; - - mutable std::mutex m_mutex; }; } // namespace lldb_private diff --git a/lldb/include/lldb/Interpreter/OptionValueArch.h b/lldb/include/lldb/Interpreter/OptionValueArch.h index 8b6954f03dd29..d5092fe788691 100644 --- a/lldb/include/lldb/Interpreter/OptionValueArch.h +++ b/lldb/include/lldb/Interpreter/OptionValueArch.h @@ -12,6 +12,7 @@ #include "lldb/Interpreter/OptionValue.h" #include "lldb/Utility/ArchSpec.h" #include "lldb/Utility/CompletionRequest.h" +#include <mutex> namespace lldb_private { @@ -45,6 +46,7 @@ class OptionValueArch : public Cloneable<OptionValueArch, OptionValue> { VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_current_value = m_default_value; m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValueArray.h b/lldb/include/lldb/Interpreter/OptionValueArray.h index 34170ef06a188..38ec01bdf51fc 100644 --- a/lldb/include/lldb/Interpreter/OptionValueArray.h +++ b/lldb/include/lldb/Interpreter/OptionValueArray.h @@ -36,6 +36,7 @@ class OptionValueArray : public Cloneable<OptionValueArray, OptionValue> { VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_values.clear(); m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValueBoolean.h b/lldb/include/lldb/Interpreter/OptionValueBoolean.h index 72c1ce446b8a0..e9ac654ed5e3e 100644 --- a/lldb/include/lldb/Interpreter/OptionValueBoolean.h +++ b/lldb/include/lldb/Interpreter/OptionValueBoolean.h @@ -38,6 +38,7 @@ class OptionValueBoolean : public Cloneable<OptionValueBoolean, OptionValue> { VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_current_value = m_default_value; m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValueChar.h b/lldb/include/lldb/Interpreter/OptionValueChar.h index c1f83a3daf846..e6a2ed31063a1 100644 --- a/lldb/include/lldb/Interpreter/OptionValueChar.h +++ b/lldb/include/lldb/Interpreter/OptionValueChar.h @@ -39,6 +39,7 @@ class OptionValueChar : public Cloneable<OptionValueChar, OptionValue> { VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_current_value = m_default_value; m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValueDictionary.h b/lldb/include/lldb/Interpreter/OptionValueDictionary.h index 800b7fc687640..8a28ee81585a4 100644 --- a/lldb/include/lldb/Interpreter/OptionValueDictionary.h +++ b/lldb/include/lldb/Interpreter/OptionValueDictionary.h @@ -41,6 +41,7 @@ class OptionValueDictionary VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_values.clear(); m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValueEnumeration.h b/lldb/include/lldb/Interpreter/OptionValueEnumeration.h index e8566934d9fc5..6536d1e900487 100644 --- a/lldb/include/lldb/Interpreter/OptionValueEnumeration.h +++ b/lldb/include/lldb/Interpreter/OptionValueEnumeration.h @@ -48,6 +48,7 @@ class OptionValueEnumeration VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_current_value = m_default_value; m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValueFileColonLine.h b/lldb/include/lldb/Interpreter/OptionValueFileColonLine.h index e2b84f9b81e65..e7dd0f9011078 100644 --- a/lldb/include/lldb/Interpreter/OptionValueFileColonLine.h +++ b/lldb/include/lldb/Interpreter/OptionValueFileColonLine.h @@ -36,6 +36,7 @@ class OptionValueFileColonLine : VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_file_spec.Clear(); m_line_number = LLDB_INVALID_LINE_NUMBER; m_column_number = LLDB_INVALID_COLUMN_NUMBER; diff --git a/lldb/include/lldb/Interpreter/OptionValueFileSpec.h b/lldb/include/lldb/Interpreter/OptionValueFileSpec.h index 66f2b2a04ff53..dd643703912e7 100644 --- a/lldb/include/lldb/Interpreter/OptionValueFileSpec.h +++ b/lldb/include/lldb/Interpreter/OptionValueFileSpec.h @@ -44,6 +44,7 @@ class OptionValueFileSpec : public Cloneable<OptionValueFileSpec, OptionValue> { VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_current_value = m_default_value; m_value_was_set = false; m_data_sp.reset(); diff --git a/lldb/include/lldb/Interpreter/OptionValueFormat.h b/lldb/include/lldb/Interpreter/OptionValueFormat.h index 661e8b507d64f..c5e593ff107e2 100644 --- a/lldb/include/lldb/Interpreter/OptionValueFormat.h +++ b/lldb/include/lldb/Interpreter/OptionValueFormat.h @@ -38,6 +38,7 @@ class OptionValueFormat VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_current_value = m_default_value; m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValueLanguage.h b/lldb/include/lldb/Interpreter/OptionValueLanguage.h index 41ddb2a13f15e..50c57ac2d32f7 100644 --- a/lldb/include/lldb/Interpreter/OptionValueLanguage.h +++ b/lldb/include/lldb/Interpreter/OptionValueLanguage.h @@ -40,6 +40,7 @@ class OptionValueLanguage : public Cloneable<OptionValueLanguage, OptionValue> { VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_current_value = m_default_value; m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValuePathMappings.h b/lldb/include/lldb/Interpreter/OptionValuePathMappings.h index e0aac2fd44484..0b523e7c8a7ff 100644 --- a/lldb/include/lldb/Interpreter/OptionValuePathMappings.h +++ b/lldb/include/lldb/Interpreter/OptionValuePathMappings.h @@ -36,6 +36,7 @@ class OptionValuePathMappings VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_path_mappings.Clear(m_notify_changes); m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValueRegex.h b/lldb/include/lldb/Interpreter/OptionValueRegex.h index 2799fea1538dc..4f544d086ac96 100644 --- a/lldb/include/lldb/Interpreter/OptionValueRegex.h +++ b/lldb/include/lldb/Interpreter/OptionValueRegex.h @@ -37,6 +37,7 @@ class OptionValueRegex : public Cloneable<OptionValueRegex, OptionValue> { VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_regex = RegularExpression(m_default_regex_str); m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValueSInt64.h b/lldb/include/lldb/Interpreter/OptionValueSInt64.h index f19f3f8ab875e..b5295c20bcc8c 100644 --- a/lldb/include/lldb/Interpreter/OptionValueSInt64.h +++ b/lldb/include/lldb/Interpreter/OptionValueSInt64.h @@ -44,6 +44,7 @@ class OptionValueSInt64 : public Cloneable<OptionValueSInt64, OptionValue> { VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_current_value = m_default_value; m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValueString.h b/lldb/include/lldb/Interpreter/OptionValueString.h index e199443fa8b49..8b4fc6c635839 100644 --- a/lldb/include/lldb/Interpreter/OptionValueString.h +++ b/lldb/include/lldb/Interpreter/OptionValueString.h @@ -78,6 +78,7 @@ class OptionValueString : public Cloneable<OptionValueString, OptionValue> { VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_current_value = m_default_value; m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValueUInt64.h b/lldb/include/lldb/Interpreter/OptionValueUInt64.h index 2a87c19c54bbf..678c3e035541d 100644 --- a/lldb/include/lldb/Interpreter/OptionValueUInt64.h +++ b/lldb/include/lldb/Interpreter/OptionValueUInt64.h @@ -47,6 +47,7 @@ class OptionValueUInt64 : public Cloneable<OptionValueUInt64, OptionValue> { VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_current_value = m_default_value; m_value_was_set = false; } diff --git a/lldb/include/lldb/Interpreter/OptionValueUUID.h b/lldb/include/lldb/Interpreter/OptionValueUUID.h index 2b7d9e41bcf77..7d4e6385f27f3 100644 --- a/lldb/include/lldb/Interpreter/OptionValueUUID.h +++ b/lldb/include/lldb/Interpreter/OptionValueUUID.h @@ -38,6 +38,7 @@ class OptionValueUUID : public Cloneable<OptionValueUUID, OptionValue> { VarSetOperationType op = eVarSetOperationAssign) override; void Clear() override { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_uuid.Clear(); m_value_was_set = false; } diff --git a/lldb/source/Interpreter/OptionValueFormatEntity.cpp b/lldb/source/Interpreter/OptionValueFormatEntity.cpp index b31dd4e475878..60b7b52badc9d 100644 --- a/lldb/source/Interpreter/OptionValueFormatEntity.cpp +++ b/lldb/source/Interpreter/OptionValueFormatEntity.cpp @@ -29,6 +29,7 @@ OptionValueFormatEntity::OptionValueFormatEntity(const char *default_format) { } void OptionValueFormatEntity::Clear() { + std::lock_guard<std::recursive_mutex> lock(m_mutex); m_current_entry = m_default_entry; m_current_format = m_default_format; m_value_was_set = false; diff --git a/lldb/source/Interpreter/OptionValueProperties.cpp b/lldb/source/Interpreter/OptionValueProperties.cpp index e62c15ec36da3..705e53d50cb58 100644 --- a/lldb/source/Interpreter/OptionValueProperties.cpp +++ b/lldb/source/Interpreter/OptionValueProperties.cpp @@ -304,6 +304,7 @@ OptionValueString *OptionValueProperties::GetPropertyAtIndexAsOptionValueString( } void OptionValueProperties::Clear() { + std::lock_guard<std::recursive_mutex> lock(m_mutex); const size_t num_properties = m_properties.size(); for (size_t i = 0; i < num_properties; ++i) m_properties[i].GetValue()->Clear(); _______________________________________________ lldb-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
