1
2
3
4
5 package ssacompile
6
7 import (
8 "cmd/compile/internal/ssa"
9 "cmd/compile/internal/ssa/ssaop"
10 )
11
12
13
14
15
16
17
18
19 func tightenTupleSelectors(f *ssa.Func) {
20 selectors := make(map[struct {
21 id ssa.ID
22 which int
23 }]*ssa.Value)
24 for _, b := range f.Blocks {
25 for _, selector := range b.Values {
26
27 var tuple *ssa.Value
28 idx := 0
29 switch selector.Op {
30 default:
31 continue
32 case ssaop.OpSelect1:
33 idx = 1
34 fallthrough
35 case ssaop.OpSelect0:
36 tuple = selector.Args[0]
37 if !tuple.Type.IsTuple() {
38 f.Fatalf("arg of tuple selector %s is not a tuple: %s", selector.String(), tuple.LongString())
39 }
40 case ssaop.OpSelectN:
41 tuple = selector.Args[0]
42 idx = int(selector.AuxInt)
43 if !tuple.Type.IsResults() {
44 f.Fatalf("arg of result selector %s is not a results: %s", selector.String(), tuple.LongString())
45 }
46 }
47
48
49
50
51 key := struct {
52 id ssa.ID
53 which int
54 }{tuple.ID, idx}
55 if t := selectors[key]; t != nil {
56 if selector != t {
57 selector.CopyOf(t)
58 }
59 continue
60 }
61
62
63
64 if selector.Block != tuple.Block {
65 t := selector.CopyInto(tuple.Block)
66 selector.CopyOf(t)
67 selectors[key] = t
68 continue
69 }
70
71
72
73 selectors[key] = selector
74 }
75 }
76 }
77
View as plain text