@@ -15,19 +15,32 @@ import CBasicBridging
1515import SwiftSyntax
1616import swiftLLVMJSON
1717
18- enum PluginError : Error {
19- case stalePlugin
20- case failedToSendMessage
21- case failedToReceiveMessage
22- case invalidReponseKind
18+ enum PluginError : String , Error , CustomStringConvertible {
19+ case stalePlugin = " plugin is stale "
20+ case failedToSendMessage = " failed to send request to plugin "
21+ case failedToReceiveMessage = " failed to receive result from plugin "
22+ case invalidReponseKind = " plugin returned invalid result "
23+
24+ var description : String { rawValue }
2325}
2426
2527@_cdecl ( " swift_ASTGen_initializePlugin " )
2628public func _initializePlugin(
27- opaqueHandle: UnsafeMutableRawPointer
28- ) {
29+ opaqueHandle: UnsafeMutableRawPointer ,
30+ cxxDiagnosticEngine: UnsafeMutablePointer < UInt8 > ?
31+ ) -> Bool {
2932 let plugin = CompilerPlugin ( opaqueHandle: opaqueHandle)
30- plugin. initialize ( )
33+ let diagEngine = PluginDiagnosticsEngine ( cxxDiagnosticEngine: cxxDiagnosticEngine)
34+
35+ do {
36+ try plugin. initialize ( )
37+ return true
38+ } catch {
39+ diagEngine? . diagnose (
40+ message: " compiler plugin not loaded: ' \( plugin. executableFilePath) ; failed to initialize " ,
41+ severity: . warning)
42+ return false
43+ }
3144}
3245
3346@_cdecl ( " swift_ASTGen_deinitializePlugin " )
@@ -48,17 +61,19 @@ func swift_ASTGen_pluginServerLoadLibraryPlugin(
4861 cxxDiagnosticEngine: UnsafeMutablePointer < UInt8 > ?
4962) -> Bool {
5063 let plugin = CompilerPlugin ( opaqueHandle: opaqueHandle)
64+ let diagEngine = PluginDiagnosticsEngine ( cxxDiagnosticEngine: cxxDiagnosticEngine)
65+
66+ if plugin. capability? . features. contains ( . loadPluginLibrary) != true {
67+ // This happens only if invalid plugin server was passed to `-external-plugin-path`.
68+ diagEngine? . diagnose (
69+ message: " compiler plugin not loaded: ' \( libraryPath) ; invalid plugin server " ,
70+ severity: . warning)
71+ return false
72+ }
5173 assert ( plugin. capability? . features. contains ( . loadPluginLibrary) == true )
5274 let libraryPath = String ( cString: libraryPath)
5375 let moduleName = String ( cString: moduleName)
5476
55- let diagEngine : PluginDiagnosticsEngine ?
56- if let cxxDiagnosticEngine = cxxDiagnosticEngine {
57- diagEngine = PluginDiagnosticsEngine ( cxxDiagnosticEngine: cxxDiagnosticEngine)
58- } else {
59- diagEngine = nil
60- }
61-
6277 do {
6378 let result = try plugin. sendMessageAndWaitWithoutLock (
6479 . loadPluginLibrary( libraryPath: libraryPath, moduleName: moduleName)
@@ -69,7 +84,9 @@ func swift_ASTGen_pluginServerLoadLibraryPlugin(
6984 diagEngine? . emit ( diagnostics) ;
7085 return loaded
7186 } catch {
72- diagEngine? . diagnose ( error: error)
87+ diagEngine? . diagnose (
88+ message: " compiler plugin not loaded: ' \( libraryPath) ; \( error) " ,
89+ severity: . warning)
7390 return false
7491 }
7592}
@@ -136,20 +153,15 @@ struct CompilerPlugin {
136153 }
137154
138155 /// Initialize the plugin. This should be called inside lock.
139- func initialize( ) {
140- do {
141- // Get capability.
142- let response = try self . sendMessageAndWaitWithoutLock ( . getCapability)
143- guard case . getCapabilityResult( let capability) = response else {
144- throw PluginError . invalidReponseKind
145- }
146- let ptr = UnsafeMutablePointer< Capability> . allocate( capacity: 1 )
147- ptr. initialize ( to: . init( capability) )
148- Plugin_setCapability ( opaqueHandle, UnsafeRawPointer ( ptr) )
149- } catch {
150- assertionFailure ( String ( describing: error) )
151- return
156+ func initialize( ) throws {
157+ // Get capability.
158+ let response = try self . sendMessageAndWaitWithoutLock ( . getCapability)
159+ guard case . getCapabilityResult( let capability) = response else {
160+ throw PluginError . invalidReponseKind
152161 }
162+ let ptr = UnsafeMutablePointer< Capability> . allocate( capacity: 1 )
163+ ptr. initialize ( to: . init( capability) )
164+ Plugin_setCapability ( opaqueHandle, UnsafeRawPointer ( ptr) )
153165 }
154166
155167 func deinitialize( ) {
@@ -169,6 +181,10 @@ struct CompilerPlugin {
169181 }
170182 return nil
171183 }
184+
185+ var executableFilePath : String {
186+ return String ( cString: Plugin_getExecutableFilePath ( opaqueHandle) )
187+ }
172188}
173189
174190class PluginDiagnosticsEngine {
@@ -179,6 +195,14 @@ class PluginDiagnosticsEngine {
179195 self . cxxDiagnosticEngine = cxxDiagnosticEngine
180196 }
181197
198+ /// Failable convenience initializer for optional cxx engine pointer.
199+ convenience init ? ( cxxDiagnosticEngine: UnsafeMutablePointer < UInt8 > ? ) {
200+ guard let cxxDiagnosticEngine = cxxDiagnosticEngine else {
201+ return nil
202+ }
203+ self . init ( cxxDiagnosticEngine: cxxDiagnosticEngine)
204+ }
205+
182206 /// Register an 'ExportedSourceFile' to the engine. So the engine can get
183207 /// C++ SourceLoc from a pair of filename and offset.
184208 func add( exportedSourceFile: UnsafePointer < ExportedSourceFile > ) {
@@ -282,6 +306,10 @@ class PluginDiagnosticsEngine {
282306 )
283307 }
284308
309+ func diagnose( message: String , severity: PluginMessage . Diagnostic . Severity ) {
310+ self . emitSingle ( message: message, severity: severity, position: . invalid)
311+ }
312+
285313 /// Produce the C++ source location for a given position based on a
286314 /// syntax node.
287315 private func cxxSourceLocation(
0 commit comments