• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1#!/usr/bin/env ruby
2
3# Copyright (c) 2021-2022 Huawei Device Co., Ltd.
4# Licensed under the Apache License, Version 2.0 (the "License");
5# you may not use this file except in compliance with the License.
6# You may obtain a copy of the License at
7#
8# http://www.apache.org/licenses/LICENSE-2.0
9#
10# Unless required by applicable law or agreed to in writing, software
11# distributed under the License is distributed on an "AS IS" BASIS,
12# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13# See the License for the specific language governing permissions and
14# limitations under the License.
15
16include_relative 'common.irt'
17
18function(:IrtocTestCfg, params: {"buf" => 'ptr', "size" => 'u64'}, mode: [:Native]) {
19    if Options.arch == :arm32
20      Intrinsic(:UNREACHABLE).Terminator.void
21      ReturnVoid().void
22      next
23    end
24
25    i0 := 0
26    r0 := 0
27    While((i := (i_phi := Phi(i0, i1).u64)), size).NE {
28        res := WhilePhi(r0, phi2).u64
29
30        offset := Mul(i, 8).u64
31        value := Load(buf, offset).u64
32        If(And(i, 1).u64, 0).EQ {
33            If(And(value, 1).u64, 0).EQ {
34                r1 := Add(res, 2).u64
35                v0 := Add(value, 2).u64
36                Store(buf, offset, v0).u64
37            } Else {
38                r2 := Add(res, 1).u64
39                v1 := Add(value, 1).u64
40                Store(buf, offset, v1).u64
41            }
42            phi1 := Phi(r1, r2).u64
43        } Else {
44            r3 := Sub(res, 1).u64
45            v2 := Sub(value, 1).u64
46            Store(buf, offset, v2).u64
47        }
48        phi2 := Phi(phi1, r3).u64
49        i1 := Add(i, 1).u64
50    }
51    Return(res).u64
52}
53
54function(:IrtocTestCfgLabels, params: {"buf" => 'ptr', "size" => 'u64'}, mode: [:Native]) {
55    if Options.arch == :arm32
56      Intrinsic(:UNREACHABLE).Terminator.void
57      ReturnVoid().void
58      next
59    end
60    i0 := 0
61    r0 := 0
62
63    Label(:Head)
64    i_phi := Phi(i0, i1).u64
65    res := Phi(r0, phi2).u64
66    i := i_phi
67    If(i, size).EQ.Unlikely {
68      Goto(:Exit)
69    }
70
71    offset := Mul(i, 8).u64
72    value := Load(buf, offset).u64
73
74    If(And(i, 1).u64, 0).NE { Goto(:Else1) }
75        If(And(value, 1).u64, 0).NE { Goto(:Else2) }
76            r1 := Add(res, 2).u64
77            v0 := Add(value, 2).u64
78            Store(buf, offset, v0).u64
79            Goto(:IfCont2)
80        Label(:Else2)
81            r2 := Add(res, 1).u64
82            v1 := Add(value, 1).u64
83            Store(buf, offset, v1).u64
84        Label(:IfCont2)
85        phi1 := Phi(r1, r2).u64
86        Goto(:IfCont1)
87    Label(:Else1)
88        r3 := Sub(res, 1).u64
89        v2 := Sub(value, 1).u64
90        Store(buf, offset, v2).u64
91    Label(:IfCont1)
92    phi2 := Phi(phi1, r3).u64
93    i1 := Add(i, 1).u64
94    Goto(:Head)
95    Label(:Exit)
96    Return(res).u64
97}
98
99function(:IrtocTestAddValues, params: {a: 'i64', b: 'i64'}, mode: [:Native]) {
100    v := Add(a, b).i64
101    Return(v).i64
102}
103
104function(:IrtocTestIncMaxValue, params: {a: 'u64', b: 'u64'}, mode: [:Native]) {
105    If(a, b).GE {
106        v1 := Add(a, 1).u64
107    }
108    Else {
109        v2 := Add(b, 1).u64
110    }
111    phi := Phi(v1, v2).u64
112    Return(phi).u64
113}
114
115function(:IrtocTestIncMaxValueLabels, params: {a: 'u64', b: 'u64'}, mode: [:Native]) {
116    If(a, b).GE {
117        Goto(:l1)
118    } Else {
119        Goto(:l2)
120    }
121Label(:l1)
122    v1 := Add(a, 1).u64
123    Goto(:l3)
124Label(:l2)
125    v2 := Add(b, 1).u64
126Label(:l3)
127    Return(Phi(v1, v2).u64).u64
128}
129
130function(:IrtocTestSeqLabels, params: {a: 'u64'}, mode: [:Native]) {
131    If(a, 10).LE {
132       ret1 := AddI(a).Imm(1).u64
133       Goto(:end)
134    }
135    If(a, 100).LE {
136       ret2 := AddI(a).Imm(2).u64
137       Goto(:end)
138    }
139    ret3 := AddI(a).Imm(3).u64
140Label(:end)
141    Return(Phi(ret1, ret2, ret3).u64).u64
142}
143
144# Return `TestCall(TestCall(n) * n)`
145function(:IrtocTestRelocations, params: {"n" => 'u32'}, mode: [:Native]) {
146    res := Call(n).Method("TestCall").u32
147    res := Mul(res, n).u32
148    res := Call(res).Method("TestCall").u32
149    Return(res).u32
150}
151
152function(:IrtocTestRelocations2,
153            params: {a0: 'word', a1: 'word', f0: 'f64', a2: 'word', a3: 'word', a4: 'word', f1: 'f64', f2: 'f64', a5: 'word', a6: 'word', f3: 'f64', a7: 'word', a8: 'word', a9: 'word', f4: 'f64'}, mode: [:Native]) {
154    fres := Call(f0).Method("IncrementFloat").f64
155    fres := Add(fres, Call(f1).Method("IncrementFloat").f64).f64
156    fres := Add(fres, Call(f2).Method("IncrementFloat").f64).f64
157    fres := Add(fres, Call(f3).Method("IncrementFloat").f64).f64
158    fres := Add(fres, Call(f4).Method("IncrementFloat").f64).f64
159    ares := Call(a0).Method("IncrementInt").word
160    ares := Add(ares, Call(a1).Method("IncrementInt").word).word
161    ares := Add(ares, Call(a2).Method("IncrementInt").word).word
162    ares := Add(ares, Call(a3).Method("IncrementInt").word).word
163    ares := Add(ares, Call(a4).Method("IncrementInt").word).word
164    ares := Add(ares, Call(a5).Method("IncrementInt").word).word
165    ares := Add(ares, Call(a6).Method("IncrementInt").word).word
166    ares := Add(ares, Call(a7).Method("IncrementInt").word).word
167    ares := Add(ares, Call(a8).Method("IncrementInt").word).word
168    ares := Add(ares, Call(a9).Method("IncrementInt").word).word
169
170    res := Add(ares, Cast(fres).SrcType("DataType::FLOAT64").word).word
171    Return(res).word
172}
173
174# Return sum of all numbers from 0 to `n`
175# Fixed issue: #6890
176# Problem: `Goto` right after `If` block with only `Goto` inside leads to wrong graph
177function(:IrtocTestLabels, params: {n: 'word'}, mode: [:Native]) {
178    res_init := 0
179    i_init := 0
180Label(:Header)
181    res := Phi(res_init, res_next).word
182    i := Phi(i_init, i_next).word
183
184    res_next := Add(res, i).word
185    i_next := AddI(i).Imm(1).word
186    If(i_next, n).GT.Unlikely.b {
187        Goto(:Tail)
188    }
189    Goto(:Header)
190Label(:Tail)
191    Return(res_next).word
192}
193
194function(:IrtocTestReturnBeforeLabel, params: {n: 'word'}, mode: [:Native]) {
195    If(n, 100).GT.b {
196        Goto(:Exit1)
197    } Else {
198        Goto(:Exit2)
199    }
200Label(:Exit1)
201    Return(1).word
202Label(:Exit2)
203    Return(2).word
204}
205