3 * Copyright (c) 2018 Collabora LTD
5 * Author: Gert Wollny <gert.wollny@collabora.com>
7 * Permission is hereby granted, free of charge, to any person obtaining a
8 * copy of this software and associated documentation files (the "Software"),
9 * to deal in the Software without restriction, including without limitation
10 * on the rights to use, copy, modify, merge, publish, distribute, sub
11 * license, and/or sell copies of the Software, and to permit persons to whom
12 * the Software is furnished to do so, subject to the following conditions:
14 * The above copyright notice and this permission notice (including the next
15 * paragraph) shall be included in all copies or substantial portions of the
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20 * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
21 * THE AUTHOR(S) AND/OR THEIR SUPPLIERS BE LIABLE FOR ANY CLAIM,
22 * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
23 * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
24 * USE OR OTHER DEALINGS IN THE SOFTWARE.
27 #include "sfn_value.h"
28 #include "util/macros.h"
36 using std::unique_ptr
;
37 using std::make_shared
;
39 const char *Value::component_names
= "xyzw01?_!";
47 Value::Value(Type type
, uint32_t chan
):
56 Value::Value(Type type
):
61 Value::Type
Value::type() const
66 void Value::set_chan(uint32_t chan
)
71 void Value::print(std::ostream
& os
) const
76 void Value::print(std::ostream
& os
, const PrintFlags
& flags
) const
78 if (flags
.flags
& PrintFlags::has_neg
) os
<< '-';
79 if (flags
.flags
& PrintFlags::has_abs
) os
<< '|';
81 if (flags
.flags
& PrintFlags::has_abs
) os
<< '|';
84 void Value::do_print(std::ostream
& os
, const PrintFlags
& flags
) const
90 bool Value::operator < (const Value
& lhs
) const
92 return sel() < lhs
.sel() ||
93 (sel() == lhs
.sel() && chan() < lhs
.chan());
97 LiteralValue::LiteralValue(float value
, uint32_t chan
):
98 Value(Value::literal
, chan
)
104 LiteralValue::LiteralValue(uint32_t value
, uint32_t chan
):
105 Value(Value::literal
, chan
)
110 LiteralValue::LiteralValue(int value
, uint32_t chan
):
111 Value(Value::literal
, chan
)
116 uint32_t LiteralValue::sel() const
118 return ALU_SRC_LITERAL
;
121 uint32_t LiteralValue::value() const
126 float LiteralValue::value_float() const
131 void LiteralValue::do_print(std::ostream
& os
) const
133 os
<< "[0x" << std::setbase(16) << m_value
.u
<< " " << std::setbase(10)
134 << m_value
.f
<< "].";
135 os
<< component_names
[chan()];
138 void LiteralValue::do_print(std::ostream
& os
, UNUSED
const PrintFlags
& flags
) const
140 os
<< "[0x" << std::setbase(16) << m_value
.u
<< " "
143 os
<< m_value
.f
<< "f";
148 bool LiteralValue::is_equal_to(const Value
& other
) const
150 assert(other
.type() == Value::Type::literal
);
151 const auto& rhs
= static_cast<const LiteralValue
&>(other
);
152 return (sel() == rhs
.sel() &&
153 value() == rhs
.value());
156 SpecialValue::SpecialValue(Type type
, int value
, int chan
):
158 m_value(static_cast<AluInlineConstants
>(value
))
162 uint32_t SpecialValue::sel() const
168 void SpecialValue::do_print(std::ostream
& os
) const
170 auto sv_info
= alu_src_const
.find(m_value
);
171 if (sv_info
!= alu_src_const
.end()) {
172 os
<< sv_info
->second
.descr
;
173 if (sv_info
->second
.use_chan
)
174 os
<< '.' << component_names
[chan()];
176 os
<< "." << component_names
[chan()]
177 << " (W: Channel ignored)";
179 if (m_value
>= ALU_SRC_PARAM_BASE
&& m_value
< ALU_SRC_PARAM_BASE
+ 32)
180 os
<< " Param" << m_value
- ALU_SRC_PARAM_BASE
;
182 os
<< " E: unknown inline constant " << m_value
;
186 PValue
Value::zero(new InlineConstValue(ALU_SRC_0
, 0));
187 PValue
Value::one_f(new InlineConstValue(ALU_SRC_1
, 0));
188 PValue
Value::one_i(new InlineConstValue(ALU_SRC_1_INT
, 0));
189 PValue
Value::zero_dot_5(new InlineConstValue(ALU_SRC_0_5
, 0));
191 InlineConstValue::InlineConstValue(int value
, int chan
):
192 SpecialValue(Value::cinline
, value
, chan
)
196 bool InlineConstValue::is_equal_to(const Value
& other
) const
198 assert(other
.type() == Value::Type::cinline
);
199 const auto& rhs
= static_cast<const InlineConstValue
&>(other
);
200 return sel() == rhs
.sel();
203 UniformValue::UniformValue(uint32_t sel
, uint32_t chan
, uint32_t kcache_bank
):
204 Value(Value::kconst
, chan
)
207 m_kcache_bank
= kcache_bank
;
210 UniformValue::UniformValue(uint32_t sel
, uint32_t chan
, PValue addr
):
211 Value(Value::kconst
, chan
),
219 uint32_t UniformValue::sel() const
221 const int bank_base
[4] = {128, 160, 256, 288};
222 return m_index
< 512 ? m_index
+ bank_base
[m_kcache_bank
] : m_index
;
225 uint32_t UniformValue::kcache_bank() const
227 return m_kcache_bank
;
230 bool UniformValue::is_equal_to(const Value
& other
) const
232 const UniformValue
& o
= static_cast<const UniformValue
&>(other
);
233 return sel() == o
.sel() &&
234 m_kcache_bank
== o
.kcache_bank();
237 void UniformValue::do_print(std::ostream
& os
) const
240 os
<< "KC" << m_kcache_bank
<< "[" << m_index
;
242 os
<< "KCX[" << m_index
;
243 os
<< "]." << component_names
[chan()];