base,cpu,sim: Stop including arch/vtophys.hh when not using vtophys.
[gem5.git] / src / cpu / timing_expr.cc
1 /*
2 * Copyright (c) 2013-2014 ARM Limited
3 * All rights reserved.
4 *
5 * The license below extends only to copyright in the software and shall
6 * not be construed as granting a license to any other intellectual
7 * property including but not limited to intellectual property relating
8 * to a hardware implementation of the functionality of the software
9 * licensed hereunder. You may use the software subject to the license
10 * terms below provided that you ensure that this notice is replicated
11 * unmodified and in its entirety in all distributions of the software,
12 * modified or unmodified, in source code or in binary form.
13 *
14 * Redistribution and use in source and binary forms, with or without
15 * modification, are permitted provided that the following conditions are
16 * met: redistributions of source code must retain the above copyright
17 * notice, this list of conditions and the following disclaimer;
18 * redistributions in binary form must reproduce the above copyright
19 * notice, this list of conditions and the following disclaimer in the
20 * documentation and/or other materials provided with the distribution;
21 * neither the name of the copyright holders nor the names of its
22 * contributors may be used to endorse or promote products derived from
23 * this software without specific prior written permission.
24 *
25 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
26 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
27 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
28 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
29 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
30 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
31 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
32 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
33 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
34 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
35 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
36 */
37
38 #include "cpu/timing_expr.hh"
39
40 #include "base/intmath.hh"
41
42 TimingExprEvalContext::TimingExprEvalContext(const StaticInstPtr &inst_,
43 ThreadContext *thread_,
44 TimingExprLet *let_) :
45 inst(inst_), thread(thread_), let(let_)
46 {
47 /* Reserve space to hold the results of evaluating the
48 * let expressions */
49 if (let) {
50 unsigned int num_defns = let->defns.size();
51
52 results.resize(num_defns, 0);
53 resultAvailable.resize(num_defns, false);
54 }
55 }
56
57 uint64_t TimingExprSrcReg::eval(TimingExprEvalContext &context)
58 {
59 return context.inst->srcRegIdx(index).index();
60 }
61
62 uint64_t TimingExprReadIntReg::eval(TimingExprEvalContext &context)
63 {
64 return context.thread->readIntReg(reg->eval(context));
65 }
66
67 uint64_t TimingExprLet::eval(TimingExprEvalContext &context)
68 {
69 TimingExprEvalContext new_context(context.inst,
70 context.thread, this);
71
72 return expr->eval(new_context);
73 }
74
75 uint64_t TimingExprRef::eval(TimingExprEvalContext &context)
76 {
77 /* Lookup the result, evaluating if necessary. @todo, this
78 * should have more error checking */
79 if (!context.resultAvailable[index]) {
80 context.results[index] = context.let->defns[index]->eval(context);
81 context.resultAvailable[index] = true;
82 }
83
84 return context.results[index];
85 }
86
87 uint64_t TimingExprUn::eval(TimingExprEvalContext &context)
88 {
89 uint64_t arg_value = arg->eval(context);
90 uint64_t ret = 0;
91
92 switch (op) {
93 case Enums::timingExprSizeInBits:
94 if (arg_value == 0)
95 ret = 0;
96 else
97 ret = ceilLog2(arg_value);
98 break;
99 case Enums::timingExprNot:
100 ret = arg_value != 0;
101 break;
102 case Enums::timingExprInvert:
103 ret = ~arg_value;
104 break;
105 case Enums::timingExprSignExtend32To64:
106 ret = static_cast<int64_t>(
107 static_cast<int32_t>(arg_value));
108 break;
109 case Enums::timingExprAbs:
110 if (static_cast<int64_t>(arg_value) < 0)
111 ret = -arg_value;
112 else
113 ret = arg_value;
114 break;
115 default:
116 break;
117 }
118
119 return ret;
120 }
121
122 uint64_t TimingExprBin::eval(TimingExprEvalContext &context)
123 {
124 uint64_t left_value = left->eval(context);
125 uint64_t right_value = right->eval(context);
126 uint64_t ret = 0;
127
128 switch (op) {
129 case Enums::timingExprAdd:
130 ret = left_value + right_value;
131 break;
132 case Enums::timingExprSub:
133 ret = left_value - right_value;
134 break;
135 case Enums::timingExprUMul:
136 ret = left_value * right_value;
137 break;
138 case Enums::timingExprUDiv:
139 if (right_value != 0) {
140 ret = left_value / right_value;
141 }
142 break;
143 case Enums::timingExprUCeilDiv:
144 if (right_value != 0) {
145 ret = (left_value + (right_value - 1)) / right_value;
146 }
147 break;
148 case Enums::timingExprSMul:
149 ret = static_cast<int64_t>(left_value) *
150 static_cast<int64_t>(right_value);
151 break;
152 case Enums::timingExprSDiv:
153 if (right_value != 0) {
154 ret = static_cast<int64_t>(left_value) /
155 static_cast<int64_t>(right_value);
156 }
157 break;
158 case Enums::timingExprEqual:
159 ret = left_value == right_value;
160 break;
161 case Enums::timingExprNotEqual:
162 ret = left_value != right_value;
163 break;
164 case Enums::timingExprULessThan:
165 ret = left_value < right_value;
166 break;
167 case Enums::timingExprUGreaterThan:
168 ret = left_value > right_value;
169 break;
170 case Enums::timingExprSLessThan:
171 ret = static_cast<int64_t>(left_value) <
172 static_cast<int64_t>(right_value);
173 break;
174 case Enums::timingExprSGreaterThan:
175 ret = static_cast<int64_t>(left_value) >
176 static_cast<int64_t>(right_value);
177 break;
178 case Enums::timingExprAnd:
179 ret = (left_value != 0) && (right_value != 0);
180 break;
181 case Enums::timingExprOr:
182 ret = (left_value != 0) || (right_value != 0);
183 break;
184 default:
185 break;
186 }
187
188 return ret;
189 }
190
191 uint64_t TimingExprIf::eval(TimingExprEvalContext &context)
192 {
193 uint64_t cond_value = cond->eval(context);
194
195 if (cond_value != 0)
196 return trueExpr->eval(context);
197 else
198 return falseExpr->eval(context);
199 }
200
201 TimingExprLiteral *
202 TimingExprLiteralParams::create()
203 {
204 return new TimingExprLiteral(this);
205 }
206
207 TimingExprSrcReg *
208 TimingExprSrcRegParams::create()
209 {
210 return new TimingExprSrcReg(this);
211 }
212
213 TimingExprReadIntReg *
214 TimingExprReadIntRegParams::create()
215 {
216 return new TimingExprReadIntReg(this);
217 }
218
219 TimingExprLet *
220 TimingExprLetParams::create()
221 {
222 return new TimingExprLet(this);
223 }
224
225 TimingExprRef *
226 TimingExprRefParams::create()
227 {
228 return new TimingExprRef(this);
229 }
230
231 TimingExprUn *
232 TimingExprUnParams::create()
233 {
234 return new TimingExprUn(this);
235 }
236
237 TimingExprBin *
238 TimingExprBinParams::create()
239 {
240 return new TimingExprBin(this);
241 }
242
243 TimingExprIf *
244 TimingExprIfParams::create()
245 {
246 return new TimingExprIf(this);
247 }