Skip to content

Commit 60dae80

Browse files
committed
[lldb] Initialize SwiftASTContext with embedded swift feature
In order for expression evaluation to work when debugging embedded swift programs, the compiler instance needs to be initialized with the embedded feature. The compiler writes "-enable-embedded-swift" into the CU's debug info when compiling in embedded Swift.
1 parent 23f3e51 commit 60dae80

File tree

8 files changed

+89
-0
lines changed

8 files changed

+89
-0
lines changed

lldb/include/lldb/Core/Module.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -823,6 +823,8 @@ class Module : public std::enable_shared_from_this<Module>,
823823
std::optional<lldb::user_id_t> debugger_id);
824824

825825
bool IsSwiftCxxInteropEnabled();
826+
827+
bool IsEmbeddedSwift();
826828
#endif
827829

828830
// Return true if the file backing this module has changed since the module
@@ -1109,6 +1111,7 @@ class Module : public std::enable_shared_from_this<Module>,
11091111
void ReportErrorIfModifyDetected(const llvm::formatv_object_base &payload);
11101112
#ifdef LLDB_ENABLE_SWIFT
11111113
LazyBool m_is_swift_cxx_interop_enabled = eLazyBoolCalculate;
1114+
LazyBool m_is_embedded_swift = eLazyBoolCalculate;
11121115
#endif
11131116
};
11141117

lldb/include/lldb/Target/Target.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1289,6 +1289,8 @@ class Target : public std::enable_shared_from_this<Target>,
12891289
bool IsSwiftREPL();
12901290

12911291
bool IsSwiftCxxInteropEnabled();
1292+
1293+
bool IsEmbeddedSwift();
12921294
private:
12931295
void DisplayFallbackSwiftContextErrors(
12941296
SwiftASTContextForExpressions *swift_ast_ctx);

lldb/source/Core/Module.cpp

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1203,6 +1203,34 @@ bool Module::IsSwiftCxxInteropEnabled() {
12031203
}
12041204
return m_is_swift_cxx_interop_enabled == eLazyBoolYes;
12051205
}
1206+
1207+
bool Module::IsEmbeddedSwift() {
1208+
switch (m_is_embedded_swift) {
1209+
case eLazyBoolYes:
1210+
return true;
1211+
case eLazyBoolNo:
1212+
return false;
1213+
case eLazyBoolCalculate:
1214+
auto *sym_file = GetSymbolFile();
1215+
if (!sym_file)
1216+
return false;
1217+
1218+
m_is_embedded_swift = eLazyBoolNo;
1219+
auto options = sym_file->GetCompileOptions();
1220+
StringRef enable_embedded_swift("-enable-embedded-swift");
1221+
for (auto &[_, args] : options) {
1222+
for (const char *arg : args.GetArgumentArrayRef()) {
1223+
if (enable_embedded_swift == arg) {
1224+
m_is_embedded_swift = eLazyBoolYes;
1225+
return true;
1226+
}
1227+
}
1228+
}
1229+
1230+
return m_is_embedded_swift == eLazyBoolYes;
1231+
}
1232+
}
1233+
12061234
#endif
12071235

12081236
void Module::ReportErrorIfModifyDetected(

lldb/source/Plugins/TypeSystem/Swift/SwiftASTContext.cpp

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1936,6 +1936,9 @@ SwiftASTContext::CreateInstance(lldb::LanguageType language, Module &module,
19361936
swift_ast_sp->GetLanguageOptions().EnableCXXInterop =
19371937
module.IsSwiftCxxInteropEnabled();
19381938

1939+
if (module.IsEmbeddedSwift())
1940+
swift_ast_sp->GetLanguageOptions().enableFeature(swift::Feature::Embedded);
1941+
19391942
bool found_swift_modules = false;
19401943
SymbolFile *sym_file = module.GetSymbolFile();
19411944

@@ -2357,6 +2360,10 @@ lldb::TypeSystemSP SwiftASTContext::CreateInstance(
23572360

23582361
swift_ast_sp->GetLanguageOptions().EnableCXXInterop =
23592362
target.IsSwiftCxxInteropEnabled();
2363+
2364+
if (target.IsEmbeddedSwift())
2365+
swift_ast_sp->GetLanguageOptions().enableFeature(swift::Feature::Embedded);
2366+
23602367
bool handled_sdk_path = false;
23612368
const size_t num_images = target.GetImages().GetSize();
23622369

@@ -2651,6 +2658,10 @@ lldb::TypeSystemSP SwiftASTContext::CreateInstance(
26512658

26522659
swift_ast_sp->GetLanguageOptions().EnableCXXInterop =
26532660
target.IsSwiftCxxInteropEnabled();
2661+
2662+
if (target.IsEmbeddedSwift())
2663+
swift_ast_sp->GetLanguageOptions().enableFeature(swift::Feature::Embedded);
2664+
26542665
bool handled_sdk_path = false;
26552666
const size_t num_images = target.GetImages().GetSize();
26562667

lldb/source/Target/Target.cpp

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3188,6 +3188,14 @@ bool Target::IsSwiftCxxInteropEnabled() {
31883188
return m_is_swift_cxx_interop_enabled == eLazyBoolYes;
31893189
}
31903190

3191+
bool Target::IsEmbeddedSwift() {
3192+
if (GetImages().IsEmpty())
3193+
return false;
3194+
3195+
// Embedded Swift cannot be mixed with non-embedded, so checking the first
3196+
// module should be enough.
3197+
return GetImages().GetModuleAtIndex(0)->IsEmbeddedSwift();
3198+
}
31913199
#endif // LLDB_ENABLE_SWIFT
31923200

31933201
void Target::SettingsInitialize() { Process::SettingsInitialize(); }
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
SWIFT_SOURCES := main.swift
2+
SWIFT_EMBEDDED_MODE := 1
3+
4+
include Makefile.rules
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
import lldb
2+
from lldbsuite.test.lldbtest import *
3+
from lldbsuite.test.decorators import *
4+
import lldbsuite.test.lldbutil as lldbutil
5+
import unittest2
6+
7+
8+
class TestSwiftEmbeddedExpression(TestBase):
9+
@skipUnlessDarwin
10+
@swiftTest
11+
def test(self):
12+
self.build()
13+
14+
target, process, _, _ = lldbutil.run_to_source_breakpoint(
15+
self, "break here", lldb.SBFileSpec("main.swift")
16+
)
17+
18+
self.expect("expr a.foo()", substrs=["(Int)", " = 16"])
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
struct A {
2+
var field = 4
3+
4+
func foo() -> Int {
5+
return field * field
6+
}
7+
}
8+
9+
10+
let a = A()
11+
// Dummy statement to set breakpoint print can't be used in embedded Swift for now.
12+
let dummy = A() // break here
13+
let string = StaticString("Hello")
14+
print(string)
15+

0 commit comments

Comments
 (0)