File: tuple-conformances.swift

package info (click to toggle)
swiftlang 6.0.3-2
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 2,519,992 kB
  • sloc: cpp: 9,107,863; ansic: 2,040,022; asm: 1,135,751; python: 296,500; objc: 82,456; f90: 60,502; lisp: 34,951; pascal: 19,946; sh: 18,133; perl: 7,482; ml: 4,937; javascript: 4,117; makefile: 3,840; awk: 3,535; xml: 914; fortran: 619; cs: 573; ruby: 573
file content (65 lines) | stat: -rw-r--r-- 2,626 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
// RUN: %target-swift-frontend -emit-sil %s -enable-experimental-feature TupleConformances | %FileCheck %s

// Required for experimental features
// REQUIRES: asserts

public typealias Tuple<each T> = (repeat each T)

public protocol P {
  static func protocolMethod()
}

extension Tuple: P where repeat each T: P {
  public static func protocolMethod() {}
}

extension Int: P {
  public static func protocolMethod() {}
}

public func callee<T: P>(t: T.Type) {
}

@_transparent
public func transparentCallee<T: P>(t: T.Type) {
  t.protocolMethod()
}

// Make sure we don't devirtualize the call when we inline transparentCallee()
// into transparentCaller(), because we might unwrap the tuple conformance
// later.

// CHECK-LABEL: sil [transparent] @$s4main17transparentCaller5tupleyxxQp_tm_tRvzAA1PRzlF : $@convention(thin) <each T where repeat each T : P> (@thin (repeat each T).Type) -> () {
@_transparent public func transparentCaller<each T: P>(tuple: (repeat each T).Type) {
  callee(t: tuple)

// CHECK: [[FN:%.*]] = witness_method $(repeat each T), #P.protocolMethod : <Self where Self : P> (Self.Type) -> () -> () : $@convention(witness_method: P) <τ_0_0 where τ_0_0 : P> (@thick τ_0_0.Type) -> ()
// CHECK: apply [[FN:%.*]]<(repeat each T)>({{.*}})

  transparentCallee(t: tuple)

// FIXME: This one is wrong in the AST
  tuple.protocolMethod()
}

// Inlining transparentCaller() into caller() exercises the code path to unwrap
// a one-element tuple conformance.

public func caller() {
  transparentCaller(tuple: Int.self)
}

// CHECK-LABEL: sil @$s4main6calleryyF : $@convention(thin) () -> () {
// CHECK: [[FN:%.*]] = function_ref @$s4main6callee1tyxm_tAA1PRzlF : $@convention(thin) <τ_0_0 where τ_0_0 : P> (@thick τ_0_0.Type) -> ()
// CHECK: apply [[FN]]<Int>({{.*}}) : $@convention(thin) <τ_0_0 where τ_0_0 : P> (@thick τ_0_0.Type) -> ()

// Make sure the witness method call in transparentCallee() was devirtualized to Int.protocolMethod().

// CHECK: [[FN:%.*]] = function_ref @$sSi4mainE14protocolMethodyyFZ : $@convention(method) (@thin Int.Type) -> () // user: %6
// CHECK: apply [[FN]]({{.*}}) : $@convention(method) (@thin Int.Type) -> ()

// FIXME: This is the `tuple.protocolMethod()` in transparentCaller(). It should
// also refer to Int.protocolMethod()!

// CHECK: [[FN:%.*]] = function_ref @$sBT4mainRvzAA1PRzlE14protocolMethodyyFZ : $@convention(method) <each τ_0_0 where repeat each τ_0_0 : P> (@thin (repeat each τ_0_0).Type) -> ()
// CHECK: apply [[FN]]<Pack{Int}>({{.*}}) : $@convention(method) <each τ_0_0 where repeat each τ_0_0 : P> (@thin (repeat each τ_0_0).Type) -> ()