@@ -127,25 +127,32 @@ class CallTests extends SwiftCompilerSrc2CpgSuite {
127127 | }
128128 |}
129129 |""" .stripMargin
130- val cpg = code(testCode)
131-
132- val List (fooCall) = cpg.call.nameExact(" foo" ).l
133- fooCall.methodFullName shouldBe x2cpg.Defines .DynamicCallUnknownFullName
134- fooCall.signature shouldBe " "
135- fooCall.dispatchType shouldBe DispatchTypes .DYNAMIC_DISPATCH
136-
137- val List (fooCallReceiver) = fooCall.receiver.isIdentifier.l
138- fooCallReceiver.name shouldBe " self"
139- fooCallReceiver.typeFullName shouldBe " Sources/main.swift:<global>.Foo"
140-
141- val List (barCall) = cpg.call.nameExact(" bar" ).l
142- barCall.methodFullName shouldBe x2cpg.Defines .DynamicCallUnknownFullName
143- barCall.signature shouldBe " "
144- barCall.dispatchType shouldBe DispatchTypes .DYNAMIC_DISPATCH
145-
146- val List (barCallReceiverCall) = barCall.receiver.isIdentifier.l
147- barCallReceiverCall.name shouldBe " self"
148- barCallReceiverCall.typeFullName shouldBe " Sources/main.swift:<global>.Foo"
130+ pendingUntilFixed {
131+ val cpg = code(testCode)
132+
133+ // These extension calls should be static calls.
134+ // Currently, there is no way to detect this as the swift-parser AST does not carry this information.
135+ // Hence, they are treated as dynamic calls like regular method calls.
136+ // We will leave this test in to document to current state and to remind us to fix this in the future.
137+ // TODO: Fix this once we can detect extension method calls properly. (see similar test with compiler support below)
138+ val List (fooCall) = cpg.call.nameExact(" foo" ).l
139+ fooCall.methodFullName shouldBe x2cpg.Defines .DynamicCallUnknownFullName
140+ fooCall.signature shouldBe " "
141+ fooCall.dispatchType shouldBe DispatchTypes .STATIC_DISPATCH // Should be STATIC_DISPATCH for extension methods, but it is not
142+
143+ val List (fooCallReceiver) = fooCall.receiver.isIdentifier.l
144+ fooCallReceiver.name shouldBe " self"
145+ fooCallReceiver.typeFullName shouldBe " Sources/main.swift:<global>.Foo"
146+
147+ val List (barCall) = cpg.call.nameExact(" bar" ).l
148+ barCall.methodFullName shouldBe x2cpg.Defines .DynamicCallUnknownFullName
149+ barCall.signature shouldBe " "
150+ barCall.dispatchType shouldBe DispatchTypes .STATIC_DISPATCH // Should be STATIC_DISPATCH for extension methods, but it is not
151+
152+ val List (barCallReceiverCall) = barCall.receiver.isIdentifier.l
153+ barCallReceiverCall.name shouldBe " self"
154+ barCallReceiverCall.typeFullName shouldBe " Sources/main.swift:<global>.Foo"
155+ }
149156 }
150157
151158 " be correct for simple calls to functions from extensions with compiler support" in {
@@ -162,24 +169,33 @@ class CallTests extends SwiftCompilerSrc2CpgSuite {
162169 | }
163170 |}
164171 |""" .stripMargin
165- val cpg = codeWithSwiftSetup(testCode)
166-
167- val List (fooCall) = cpg.call.nameExact(" foo" ).l
168- fooCall.methodFullName shouldBe " SwiftTest.Foo.foo:()->()"
169- fooCall.signature shouldBe " ()->()"
170- fooCall.dispatchType shouldBe DispatchTypes .DYNAMIC_DISPATCH
171- val List (fooCallReceiver) = fooCall.receiver.isIdentifier.l
172- fooCallReceiver.name shouldBe " self"
173- fooCallReceiver.typeFullName shouldBe " SwiftTest.Foo"
174172
175- val List (barCall) = cpg.call.nameExact(" bar" ).l
176- barCall.methodFullName shouldBe " SwiftTest.Foo.bar:()->()"
177- barCall.signature shouldBe " ()->()"
178- barCall.dispatchType shouldBe DispatchTypes .DYNAMIC_DISPATCH
179-
180- val List (barCallReceiverCall) = barCall.receiver.isIdentifier.l
181- barCallReceiverCall.name shouldBe " self"
182- barCallReceiverCall.typeFullName shouldBe " SwiftTest.Foo"
173+ pendingUntilFixed {
174+ // These extension calls should be static calls.
175+ // Currently, there is no way to detect this as the swift-parser AST does not carry this information.
176+ // Hence, they are treated as dynamic calls like regular method calls.
177+ // We will leave this test in to document to current state and to remind us to fix this in the future.
178+ // TODO: Fix this once we can detect extension method calls properly.
179+ // TODO: Extend the compiler info queries to be able to detect static calls reliably.
180+ val cpg = codeWithSwiftSetup(testCode)
181+
182+ val List (fooCall) = cpg.call.nameExact(" foo" ).l
183+ fooCall.methodFullName shouldBe " SwiftTest.Foo.foo:()->()"
184+ fooCall.signature shouldBe " ()->()"
185+ fooCall.dispatchType shouldBe DispatchTypes .STATIC_DISPATCH // Should be STATIC_DISPATCH for extension methods, but it is not
186+ val List (fooCallReceiver) = fooCall.receiver.isIdentifier.l
187+ fooCallReceiver.name shouldBe " self"
188+ fooCallReceiver.typeFullName shouldBe " SwiftTest.Foo"
189+
190+ val List (barCall) = cpg.call.nameExact(" bar" ).l
191+ barCall.methodFullName shouldBe " SwiftTest.Foo.bar:()->()"
192+ barCall.signature shouldBe " ()->()"
193+ barCall.dispatchType shouldBe DispatchTypes .STATIC_DISPATCH // Should be STATIC_DISPATCH for extension methods, but it is not
194+
195+ val List (barCallReceiverCall) = barCall.receiver.isIdentifier.l
196+ barCallReceiverCall.name shouldBe " self"
197+ barCallReceiverCall.typeFullName shouldBe " SwiftTest.Foo"
198+ }
183199 }
184200
185201 " be correct for simple calls to functions from protocols" in {
@@ -255,6 +271,56 @@ class CallTests extends SwiftCompilerSrc2CpgSuite {
255271 barCallReceiverCall.typeFullName shouldBe " SwiftTest.Foo"
256272 }
257273
274+ " be correct for simple calls to functions from multiple protocols with compiler support" in {
275+ val testCode =
276+ """
277+ |protocol FooProtocol {
278+ | func foo()
279+ | func bar()
280+ |}
281+ |protocol FooBarProtocol {
282+ | func foobar()
283+ |}
284+ |class Foo: FooProtocol, FooBarProtocol {
285+ | func foo() {}
286+ | func bar() {}
287+ | func foobar() {}
288+ | func main() {
289+ | foo()
290+ | self.bar()
291+ | foobar()
292+ | }
293+ |}
294+ |""" .stripMargin
295+ val cpg = codeWithSwiftSetup(testCode)
296+
297+ val List (fooCall) = cpg.call.nameExact(" foo" ).l
298+ fooCall.methodFullName shouldBe " SwiftTest.Foo.foo:()->()"
299+ fooCall.signature shouldBe " ()->()"
300+ fooCall.dispatchType shouldBe DispatchTypes .DYNAMIC_DISPATCH
301+ val List (fooCallReceiver) = fooCall.receiver.isIdentifier.l
302+ fooCallReceiver.name shouldBe " self"
303+ fooCallReceiver.typeFullName shouldBe " SwiftTest.Foo"
304+
305+ val List (barCall) = cpg.call.nameExact(" bar" ).l
306+ barCall.methodFullName shouldBe " SwiftTest.Foo.bar:()->()"
307+ barCall.signature shouldBe " ()->()"
308+ barCall.dispatchType shouldBe DispatchTypes .DYNAMIC_DISPATCH
309+
310+ val List (barCallReceiverCall) = barCall.receiver.isIdentifier.l
311+ barCallReceiverCall.name shouldBe " self"
312+ barCallReceiverCall.typeFullName shouldBe " SwiftTest.Foo"
313+
314+ val List (foobarCall) = cpg.call.nameExact(" foobar" ).l
315+ foobarCall.methodFullName shouldBe " SwiftTest.Foo.foobar:()->()"
316+ foobarCall.signature shouldBe " ()->()"
317+ foobarCall.dispatchType shouldBe DispatchTypes .DYNAMIC_DISPATCH
318+
319+ val List (foobarCallReceiverCall) = foobarCall.receiver.isIdentifier.l
320+ foobarCallReceiverCall.name shouldBe " self"
321+ foobarCallReceiverCall.typeFullName shouldBe " SwiftTest.Foo"
322+ }
323+
258324 " be correct for simple call to static function" in {
259325 // TODO: extend the GsonTypeInfoReader to query for information whether the call is a call to a static function
260326 val testCode =
0 commit comments