File: enum_jump_thread.sil

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 (131 lines) | stat: -rw-r--r-- 2,826 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
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
// RUN: %target-sil-opt -enable-sil-verify-all %s -jumpthread-simplify-cfg -cse | %FileCheck %s

// Test if jump-threading is done to combine two enum instructions
// into a single block.

sil_stage canonical

import Builtin

enum E {
  case A
  case B
}

enum E2 {
  case X
  case Y(E)
}

// CHECK-LABEL: sil @testfunc

sil @testfunc : $@convention(thin) (Builtin.Int1, Builtin.Int1) -> E2 {
bb0(%0 : $Builtin.Int1, %1 : $Builtin.Int1):
  cond_br %0, bb1, bb4

bb1:
  %2 = enum $E, #E.A!enumelt
  cond_br %1, bb2, bb3(%2 : $E)

// CHECK: [[ENUM1:%[0-9]+]] = enum $E, #E.B
// CHECK-NEXT: [[ENUM2:%[0-9]+]] = enum $E2, #E2.Y!enumelt, [[ENUM1]]
// CHECK-NEXT: br [[RETBB:bb[0-9]+]]([[ENUM2]] : $E2)
bb2:
  // This block should be jump-threaded
  %3 = enum $E, #E.B!enumelt
  br bb3(%3 : $E)

bb3(%4 : $E):
  %5 = enum $E2, #E2.Y!enumelt, %4 : $E
  br bb5(%5 : $E2)

bb4:
  %6 = enum $E2, #E2.X!enumelt
  br bb5(%6 : $E2)

// CHECK: [[RETBB]]({{.*}}):
// CHECK-NEXT: return
bb5(%7 : $E2):
  return %7 : $E2
}

// CHECK-LABEL: sil @test_enum_addr
sil @test_enum_addr : $@convention(thin) () -> Builtin.Int32 {
bb0:
  %2 = alloc_stack $E
  cond_br undef, bb1, bb2

// CHECK:       bb1:
// CHECK-NEXT:    inject_enum_addr
// CHECK-NEXT:    switch_enum_addr
bb1:
  inject_enum_addr %2 : $*E, #E.A!enumelt
  br bb3

// CHECK:       bb2:
// CHECK-NEXT:    inject_enum_addr
// CHECK-NEXT:    switch_enum_addr
bb2:
  inject_enum_addr %2 : $*E, #E.B!enumelt
  br bb3

bb3:
  switch_enum_addr %2 : $*E, case #E.A!enumelt: bb4, case #E.B!enumelt: bb5

bb4:
  %10 = integer_literal $Builtin.Int32, 1
  br bb6(%10 : $Builtin.Int32)

bb5:
  %11 = integer_literal $Builtin.Int32, 2
  br bb6(%11 : $Builtin.Int32)

bb6(%12 : $Builtin.Int32):
  dealloc_stack %2 : $*E
  return %12 : $Builtin.Int32
// CHECK: } // end sil function 'test_enum_addr'
}

// CHECK-LABEL: sil @dont_jumpthread_enum_addr
sil @dont_jumpthread_enum_addr : $@convention(thin) (E) -> Builtin.Int32 {
bb0(%0 : $E):
  %2 = alloc_stack $E
  %3 = alloc_stack $E
  cond_br undef, bb1, bb2

// CHECK:       bb1:
// CHECK-NEXT:    inject_enum_addr
// CHECK-NEXT:    store
// CHECK-NEXT:    br bb3
bb1:
  inject_enum_addr %2 : $*E, #E.A!enumelt
  store %0 to %2 : $*E
  br bb3

// CHECK:       bb2:
// CHECK-NEXT:    inject_enum_addr
// CHECK-NEXT:    br bb3
bb2:
  inject_enum_addr %3 : $*E, #E.A!enumelt
  br bb3

// CHECK:       bb3:
// CHECK-NEXT:    switch_enum_addr
bb3:
  switch_enum_addr %2 : $*E, case #E.A!enumelt: bb4, case #E.B!enumelt: bb5

bb4:
  %10 = integer_literal $Builtin.Int32, 1
  br bb6(%10 : $Builtin.Int32)

bb5:
  %11 = integer_literal $Builtin.Int32, 2
  br bb6(%11 : $Builtin.Int32)

bb6(%12 : $Builtin.Int32):
  dealloc_stack %3 : $*E
  dealloc_stack %2 : $*E
  return %12 : $Builtin.Int32
// CHECK: } // end sil function 'dont_jumpthread_enum_addr'
}