Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 1 | // Copyright 2022 The Tint Authors. |
| 2 | // |
| 3 | // Licensed under the Apache License, Version 2.0 (the "License"); |
| 4 | // you may not use this file except in compliance with the License. |
| 5 | // You may obtain a copy of the License at |
| 6 | // |
| 7 | // http://www.apache.org/licenses/LICENSE-2.0 |
| 8 | // |
| 9 | // Unless required by applicable law or agreed to in writing, software |
| 10 | // distributed under the License is distributed on an "AS IS" BASIS, |
| 11 | // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| 12 | // See the License for the specific language governing permissions and |
| 13 | // limitations under the License. |
| 14 | |
| 15 | #include "src/tint/sem/materialize.h" |
| 16 | |
| 17 | #include "src/tint/resolver/resolver.h" |
| 18 | #include "src/tint/resolver/resolver_test_helper.h" |
| 19 | #include "src/tint/sem/test_helper.h" |
| 20 | |
| 21 | #include "gmock/gmock.h" |
| 22 | |
| 23 | using namespace tint::number_suffixes; // NOLINT |
| 24 | |
| 25 | namespace tint::resolver { |
| 26 | namespace { |
| 27 | |
| 28 | using AFloatV = builder::vec<3, AFloat>; |
| 29 | using AFloatM = builder::mat<3, 2, AFloat>; |
| 30 | using AIntV = builder::vec<3, AInt>; |
| 31 | using f32V = builder::vec<3, f32>; |
| 32 | using f16V = builder::vec<3, f16>; |
| 33 | using i32V = builder::vec<3, i32>; |
| 34 | using u32V = builder::vec<3, u32>; |
| 35 | using f32M = builder::mat<3, 2, f32>; |
Ben Clayton | 22d8dea | 2022-06-20 19:23:02 +0000 | [diff] [blame] | 36 | using i32Varr = builder::array<3, i32>; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 37 | |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 38 | constexpr double kHighestU32 = static_cast<double>(u32::kHighest); |
| 39 | constexpr double kLowestU32 = static_cast<double>(u32::kLowest); |
| 40 | constexpr double kHighestI32 = static_cast<double>(i32::kHighest); |
| 41 | constexpr double kLowestI32 = static_cast<double>(i32::kLowest); |
| 42 | constexpr double kHighestF32 = static_cast<double>(f32::kHighest); |
| 43 | constexpr double kLowestF32 = static_cast<double>(f32::kLowest); |
Zhaoming Jiang | 6058882 | 2022-06-28 14:03:36 +0000 | [diff] [blame] | 44 | // constexpr double kHighestF16 = static_cast<double>(f16::kHighest); |
| 45 | // constexpr double kLowestF16 = static_cast<double>(f16::kLowest); |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 46 | constexpr double kTooBigF32 = static_cast<double>(3.5e+38); |
Zhaoming Jiang | 6058882 | 2022-06-28 14:03:36 +0000 | [diff] [blame] | 47 | // constexpr double kTooBigF16 = static_cast<double>(6.6e+4); |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 48 | constexpr double kPiF64 = 3.141592653589793; |
| 49 | constexpr double kPiF32 = 3.1415927410125732; // kPiF64 quantized to f32 |
Zhaoming Jiang | 6058882 | 2022-06-28 14:03:36 +0000 | [diff] [blame] | 50 | // constexpr double kPiF16 = 3.140625; // kPiF64 quantized to f16 |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 51 | |
| 52 | constexpr double kSubnormalF32 = 0x1.0p-128; |
Zhaoming Jiang | 6058882 | 2022-06-28 14:03:36 +0000 | [diff] [blame] | 53 | // constexpr double kSubnormalF16 = 0x1.0p-16; |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 54 | |
| 55 | enum class Expectation { |
| 56 | kMaterialize, |
| 57 | kNoMaterialize, |
| 58 | kInvalidConversion, |
| 59 | kValueCannotBeRepresented, |
| 60 | }; |
| 61 | |
| 62 | static std::ostream& operator<<(std::ostream& o, Expectation m) { |
| 63 | switch (m) { |
| 64 | case Expectation::kMaterialize: |
| 65 | return o << "materialize"; |
| 66 | case Expectation::kNoMaterialize: |
| 67 | return o << "no-materialize"; |
| 68 | case Expectation::kInvalidConversion: |
| 69 | return o << "invalid-conversion"; |
| 70 | case Expectation::kValueCannotBeRepresented: |
| 71 | return o << "value cannot be represented"; |
| 72 | } |
| 73 | return o << "<unknown>"; |
| 74 | } |
| 75 | |
Ben Clayton | aa037ac | 2022-06-29 19:07:30 +0000 | [diff] [blame] | 76 | template <typename CASE> |
| 77 | class MaterializeTest : public resolver::ResolverTestWithParam<CASE> { |
| 78 | protected: |
| 79 | using ProgramBuilder::FriendlyName; |
| 80 | |
| 81 | void CheckTypesAndValues(const sem::Expression* expr, |
| 82 | const tint::sem::Type* expected_sem_ty, |
| 83 | const std::variant<AInt, AFloat>& expected_value) { |
| 84 | std::visit([&](auto v) { CheckTypesAndValuesImpl(expr, expected_sem_ty, v); }, |
| 85 | expected_value); |
| 86 | } |
| 87 | |
| 88 | private: |
| 89 | template <typename T> |
| 90 | void CheckTypesAndValuesImpl(const sem::Expression* expr, |
| 91 | const tint::sem::Type* expected_sem_ty, |
| 92 | T expected_value) { |
| 93 | EXPECT_TYPE(expr->Type(), expected_sem_ty); |
| 94 | |
| 95 | auto* value = expr->ConstantValue(); |
| 96 | ASSERT_NE(value, nullptr); |
| 97 | EXPECT_TYPE(expr->Type(), value->Type()); |
| 98 | |
| 99 | tint::Switch( |
| 100 | expected_sem_ty, // |
| 101 | [&](const sem::Vector* v) { |
| 102 | for (uint32_t i = 0; i < v->Width(); i++) { |
| 103 | auto* el = value->Index(i); |
| 104 | ASSERT_NE(el, nullptr); |
| 105 | EXPECT_TYPE(el->Type(), v->type()); |
| 106 | EXPECT_EQ(std::get<T>(el->Value()), expected_value); |
| 107 | } |
| 108 | }, |
| 109 | [&](const sem::Matrix* m) { |
| 110 | for (uint32_t c = 0; c < m->columns(); c++) { |
| 111 | auto* column = value->Index(c); |
| 112 | ASSERT_NE(column, nullptr); |
| 113 | EXPECT_TYPE(column->Type(), m->ColumnType()); |
| 114 | for (uint32_t r = 0; r < m->rows(); r++) { |
| 115 | auto* el = column->Index(r); |
| 116 | ASSERT_NE(el, nullptr); |
| 117 | EXPECT_TYPE(el->Type(), m->type()); |
| 118 | EXPECT_EQ(std::get<T>(el->Value()), expected_value); |
| 119 | } |
| 120 | } |
| 121 | }, |
| 122 | [&](Default) { EXPECT_EQ(std::get<T>(value->Value()), expected_value); }); |
| 123 | } |
| 124 | }; |
| 125 | |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 126 | //////////////////////////////////////////////////////////////////////////////////////////////////// |
| 127 | // MaterializeAbstractNumericToConcreteType |
| 128 | // Tests that an abstract-numeric will materialize to the expected concrete type |
| 129 | //////////////////////////////////////////////////////////////////////////////////////////////////// |
| 130 | namespace materialize_abstract_numeric_to_concrete_type { |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 131 | // How should the materialization occur? |
| 132 | enum class Method { |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 133 | // var a : target_type = abstract_expr; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 134 | kVar, |
| 135 | |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 136 | // let a : target_type = abstract_expr; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 137 | kLet, |
| 138 | |
Ben Clayton | 22bd004 | 2022-05-31 20:40:59 +0000 | [diff] [blame] | 139 | // var a : target_type; |
| 140 | // a = abstract_expr; |
| 141 | kAssign, |
| 142 | |
| 143 | // _ = abstract_expr; |
| 144 | kPhonyAssign, |
| 145 | |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 146 | // fn F(v : target_type) {} |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 147 | // fn x() { |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 148 | // F(abstract_expr); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 149 | // } |
| 150 | kFnArg, |
| 151 | |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 152 | // min(target_expr, abstract_expr); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 153 | kBuiltinArg, |
| 154 | |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 155 | // fn F() : target_type { |
| 156 | // return abstract_expr; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 157 | // } |
| 158 | kReturn, |
| 159 | |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 160 | // array<target_type, 1>(abstract_expr); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 161 | kArray, |
| 162 | |
| 163 | // struct S { |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 164 | // v : target_type |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 165 | // }; |
| 166 | // fn x() { |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 167 | // _ = S(abstract_expr) |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 168 | // } |
| 169 | kStruct, |
| 170 | |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 171 | // target_expr + abstract_expr |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 172 | kBinaryOp, |
| 173 | |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 174 | // switch (abstract_expr) { |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 175 | // case target_expr: {} |
| 176 | // default: {} |
| 177 | // } |
| 178 | kSwitchCond, |
| 179 | |
| 180 | // switch (target_expr) { |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 181 | // case abstract_expr: {} |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 182 | // default: {} |
| 183 | // } |
| 184 | kSwitchCase, |
| 185 | |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 186 | // switch (abstract_expr) { |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 187 | // case 123: {} |
| 188 | // case target_expr: {} |
| 189 | // default: {} |
| 190 | // } |
| 191 | kSwitchCondWithAbstractCase, |
| 192 | |
| 193 | // switch (target_expr) { |
| 194 | // case 123: {} |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 195 | // case abstract_expr: {} |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 196 | // default: {} |
| 197 | // } |
| 198 | kSwitchCaseWithAbstractCase, |
Ben Clayton | b8ac9339 | 2022-05-28 10:34:06 +0000 | [diff] [blame] | 199 | |
| 200 | // @workgroup_size(target_expr, abstract_expr, 123) |
dan sinclair | b29892b | 2022-06-07 13:55:34 +0000 | [diff] [blame] | 201 | // @compute |
Ben Clayton | b8ac9339 | 2022-05-28 10:34:06 +0000 | [diff] [blame] | 202 | // fn f() {} |
| 203 | kWorkgroupSize |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 204 | }; |
| 205 | |
| 206 | static std::ostream& operator<<(std::ostream& o, Method m) { |
| 207 | switch (m) { |
| 208 | case Method::kVar: |
| 209 | return o << "var"; |
| 210 | case Method::kLet: |
| 211 | return o << "let"; |
Ben Clayton | 22bd004 | 2022-05-31 20:40:59 +0000 | [diff] [blame] | 212 | case Method::kAssign: |
| 213 | return o << "assign"; |
| 214 | case Method::kPhonyAssign: |
| 215 | return o << "phony-assign"; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 216 | case Method::kFnArg: |
| 217 | return o << "fn-arg"; |
| 218 | case Method::kBuiltinArg: |
| 219 | return o << "builtin-arg"; |
| 220 | case Method::kReturn: |
| 221 | return o << "return"; |
| 222 | case Method::kArray: |
| 223 | return o << "array"; |
| 224 | case Method::kStruct: |
| 225 | return o << "struct"; |
| 226 | case Method::kBinaryOp: |
| 227 | return o << "binary-op"; |
| 228 | case Method::kSwitchCond: |
| 229 | return o << "switch-cond"; |
| 230 | case Method::kSwitchCase: |
| 231 | return o << "switch-case"; |
| 232 | case Method::kSwitchCondWithAbstractCase: |
| 233 | return o << "switch-cond-with-abstract"; |
| 234 | case Method::kSwitchCaseWithAbstractCase: |
| 235 | return o << "switch-case-with-abstract"; |
Ben Clayton | b8ac9339 | 2022-05-28 10:34:06 +0000 | [diff] [blame] | 236 | case Method::kWorkgroupSize: |
| 237 | return o << "workgroup-size"; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 238 | } |
| 239 | return o << "<unknown>"; |
| 240 | } |
| 241 | |
| 242 | struct Data { |
| 243 | std::string target_type_name; |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 244 | std::string target_element_type_name; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 245 | builder::ast_type_func_ptr target_ast_ty; |
| 246 | builder::sem_type_func_ptr target_sem_ty; |
| 247 | builder::ast_expr_func_ptr target_expr; |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 248 | std::string abstract_type_name; |
| 249 | builder::ast_expr_func_ptr abstract_expr; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 250 | std::variant<AInt, AFloat> materialized_value; |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 251 | double literal_value; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 252 | }; |
| 253 | |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 254 | template <typename TARGET_TYPE, typename ABSTRACT_TYPE, typename MATERIALIZED_TYPE> |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 255 | Data Types(MATERIALIZED_TYPE materialized_value, double literal_value) { |
| 256 | using TargetDataType = builder::DataType<TARGET_TYPE>; |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 257 | using AbstractDataType = builder::DataType<ABSTRACT_TYPE>; |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 258 | using TargetElementDataType = builder::DataType<typename TargetDataType::ElementType>; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 259 | return { |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 260 | TargetDataType::Name(), // target_type_name |
| 261 | TargetElementDataType::Name(), // target_element_type_name |
| 262 | TargetDataType::AST, // target_ast_ty |
| 263 | TargetDataType::Sem, // target_sem_ty |
| 264 | TargetDataType::Expr, // target_expr |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 265 | AbstractDataType::Name(), // abstract_type_name |
| 266 | AbstractDataType::Expr, // abstract_expr |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 267 | materialized_value, |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 268 | literal_value, |
| 269 | }; |
| 270 | } |
| 271 | |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 272 | template <typename TARGET_TYPE, typename ABSTRACT_TYPE> |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 273 | Data Types() { |
| 274 | using TargetDataType = builder::DataType<TARGET_TYPE>; |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 275 | using AbstractDataType = builder::DataType<ABSTRACT_TYPE>; |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 276 | using TargetElementDataType = builder::DataType<typename TargetDataType::ElementType>; |
| 277 | return { |
| 278 | TargetDataType::Name(), // target_type_name |
| 279 | TargetElementDataType::Name(), // target_element_type_name |
| 280 | TargetDataType::AST, // target_ast_ty |
| 281 | TargetDataType::Sem, // target_sem_ty |
| 282 | TargetDataType::Expr, // target_expr |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 283 | AbstractDataType::Name(), // abstract_type_name |
| 284 | AbstractDataType::Expr, // abstract_expr |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 285 | 0_a, |
| 286 | 0.0, |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 287 | }; |
| 288 | } |
| 289 | |
| 290 | static std::ostream& operator<<(std::ostream& o, const Data& c) { |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 291 | auto print_value = [&](auto&& v) { o << v; }; |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 292 | o << "[" << c.target_type_name << " <- " << c.abstract_type_name << "] ["; |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 293 | std::visit(print_value, c.materialized_value); |
| 294 | o << " <- " << c.literal_value << "]"; |
| 295 | return o; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 296 | } |
| 297 | |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 298 | using MaterializeAbstractNumericToConcreteType = |
Ben Clayton | aa037ac | 2022-06-29 19:07:30 +0000 | [diff] [blame] | 299 | MaterializeTest<std::tuple<Expectation, Method, Data>>; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 300 | |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 301 | TEST_P(MaterializeAbstractNumericToConcreteType, Test) { |
Zhaoming Jiang | 6058882 | 2022-06-28 14:03:36 +0000 | [diff] [blame] | 302 | // Once built-in and ops using f16 is properly supported, we'll need to enable this: |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 303 | // Enable(ast::Extension::kF16); |
| 304 | |
| 305 | const auto& param = GetParam(); |
| 306 | const auto& expectation = std::get<0>(param); |
| 307 | const auto& method = std::get<1>(param); |
| 308 | const auto& data = std::get<2>(param); |
| 309 | |
| 310 | auto target_ty = [&] { return data.target_ast_ty(*this); }; |
| 311 | auto target_expr = [&] { return data.target_expr(*this, 42); }; |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 312 | auto* abstract_expr = data.abstract_expr(*this, data.literal_value); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 313 | switch (method) { |
| 314 | case Method::kVar: |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 315 | WrapInFunction(Decl(Var("a", target_ty(), abstract_expr))); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 316 | break; |
| 317 | case Method::kLet: |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 318 | WrapInFunction(Decl(Let("a", target_ty(), abstract_expr))); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 319 | break; |
Ben Clayton | 22bd004 | 2022-05-31 20:40:59 +0000 | [diff] [blame] | 320 | case Method::kAssign: |
| 321 | WrapInFunction(Decl(Var("a", target_ty(), nullptr)), Assign("a", abstract_expr)); |
| 322 | break; |
| 323 | case Method::kPhonyAssign: |
| 324 | WrapInFunction(Assign(Phony(), abstract_expr)); |
| 325 | break; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 326 | case Method::kFnArg: |
| 327 | Func("F", {Param("P", target_ty())}, ty.void_(), {}); |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 328 | WrapInFunction(CallStmt(Call("F", abstract_expr))); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 329 | break; |
| 330 | case Method::kBuiltinArg: |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 331 | WrapInFunction(CallStmt(Call("min", target_expr(), abstract_expr))); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 332 | break; |
| 333 | case Method::kReturn: |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 334 | Func("F", {}, target_ty(), {Return(abstract_expr)}); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 335 | break; |
| 336 | case Method::kArray: |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 337 | WrapInFunction(Construct(ty.array(target_ty(), 1_i), abstract_expr)); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 338 | break; |
| 339 | case Method::kStruct: |
| 340 | Structure("S", {Member("v", target_ty())}); |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 341 | WrapInFunction(Construct(ty.type_name("S"), abstract_expr)); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 342 | break; |
| 343 | case Method::kBinaryOp: |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 344 | WrapInFunction(Add(target_expr(), abstract_expr)); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 345 | break; |
| 346 | case Method::kSwitchCond: |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 347 | WrapInFunction(Switch(abstract_expr, // |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 348 | Case(target_expr()->As<ast::IntLiteralExpression>()), // |
| 349 | DefaultCase())); |
| 350 | break; |
| 351 | case Method::kSwitchCase: |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 352 | WrapInFunction(Switch(target_expr(), // |
| 353 | Case(abstract_expr->As<ast::IntLiteralExpression>()), // |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 354 | DefaultCase())); |
| 355 | break; |
| 356 | case Method::kSwitchCondWithAbstractCase: |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 357 | WrapInFunction(Switch(abstract_expr, // |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 358 | Case(Expr(123_a)), // |
| 359 | Case(target_expr()->As<ast::IntLiteralExpression>()), // |
| 360 | DefaultCase())); |
| 361 | break; |
| 362 | case Method::kSwitchCaseWithAbstractCase: |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 363 | WrapInFunction(Switch(target_expr(), // |
| 364 | Case(Expr(123_a)), // |
| 365 | Case(abstract_expr->As<ast::IntLiteralExpression>()), // |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 366 | DefaultCase())); |
| 367 | break; |
Ben Clayton | b8ac9339 | 2022-05-28 10:34:06 +0000 | [diff] [blame] | 368 | case Method::kWorkgroupSize: |
| 369 | Func("f", {}, ty.void_(), {}, |
| 370 | {WorkgroupSize(target_expr(), abstract_expr, Expr(123_a)), |
| 371 | Stage(ast::PipelineStage::kCompute)}); |
| 372 | break; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 373 | } |
| 374 | |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 375 | switch (expectation) { |
| 376 | case Expectation::kMaterialize: { |
| 377 | ASSERT_TRUE(r()->Resolve()) << r()->error(); |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 378 | auto* materialize = Sem().Get<sem::Materialize>(abstract_expr); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 379 | ASSERT_NE(materialize, nullptr); |
Ben Clayton | aa037ac | 2022-06-29 19:07:30 +0000 | [diff] [blame] | 380 | CheckTypesAndValues(materialize, data.target_sem_ty(*this), data.materialized_value); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 381 | break; |
| 382 | } |
| 383 | case Expectation::kNoMaterialize: { |
| 384 | ASSERT_TRUE(r()->Resolve()) << r()->error(); |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 385 | auto* sem = Sem().Get(abstract_expr); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 386 | ASSERT_NE(sem, nullptr); |
| 387 | EXPECT_FALSE(sem->Is<sem::Materialize>()); |
Ben Clayton | aa037ac | 2022-06-29 19:07:30 +0000 | [diff] [blame] | 388 | CheckTypesAndValues(sem, data.target_sem_ty(*this), data.materialized_value); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 389 | break; |
| 390 | } |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 391 | case Expectation::kInvalidConversion: { |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 392 | ASSERT_FALSE(r()->Resolve()); |
| 393 | std::string expect; |
| 394 | switch (method) { |
| 395 | case Method::kBuiltinArg: |
| 396 | expect = "error: no matching call to min(" + data.target_type_name + ", " + |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 397 | data.abstract_type_name + ")"; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 398 | break; |
| 399 | case Method::kBinaryOp: |
| 400 | expect = "error: no matching overload for operator + (" + |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 401 | data.target_type_name + ", " + data.abstract_type_name + ")"; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 402 | break; |
| 403 | default: |
Ben Clayton | 3aa0f81 | 2022-05-27 22:06:26 +0000 | [diff] [blame] | 404 | expect = "error: cannot convert value of type '" + data.abstract_type_name + |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 405 | "' to type '" + data.target_type_name + "'"; |
| 406 | break; |
| 407 | } |
| 408 | EXPECT_THAT(r()->error(), testing::StartsWith(expect)); |
| 409 | break; |
| 410 | } |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 411 | case Expectation::kValueCannotBeRepresented: |
| 412 | ASSERT_FALSE(r()->Resolve()); |
| 413 | EXPECT_THAT(r()->error(), testing::HasSubstr("cannot be represented as '" + |
| 414 | data.target_element_type_name + "'")); |
| 415 | break; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 416 | } |
| 417 | } |
| 418 | |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 419 | /// Methods that support scalar materialization |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 420 | constexpr Method kScalarMethods[] = { |
Ben Clayton | 22bd004 | 2022-05-31 20:40:59 +0000 | [diff] [blame] | 421 | Method::kLet, Method::kVar, Method::kAssign, Method::kFnArg, Method::kBuiltinArg, |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 422 | Method::kReturn, Method::kArray, Method::kStruct, Method::kBinaryOp, |
| 423 | }; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 424 | |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 425 | /// Methods that support vector materialization |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 426 | constexpr Method kVectorMethods[] = { |
Ben Clayton | 22bd004 | 2022-05-31 20:40:59 +0000 | [diff] [blame] | 427 | Method::kLet, Method::kVar, Method::kAssign, Method::kFnArg, Method::kBuiltinArg, |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 428 | Method::kReturn, Method::kArray, Method::kStruct, Method::kBinaryOp, |
| 429 | }; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 430 | |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 431 | /// Methods that support matrix materialization |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 432 | constexpr Method kMatrixMethods[] = { |
Ben Clayton | 22bd004 | 2022-05-31 20:40:59 +0000 | [diff] [blame] | 433 | Method::kLet, Method::kVar, Method::kAssign, Method::kFnArg, |
| 434 | Method::kReturn, Method::kArray, Method::kStruct, Method::kBinaryOp, |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 435 | }; |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 436 | |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 437 | /// Methods that support materialization for switch cases |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 438 | constexpr Method kSwitchMethods[] = { |
| 439 | Method::kSwitchCond, |
| 440 | Method::kSwitchCase, |
| 441 | Method::kSwitchCondWithAbstractCase, |
| 442 | Method::kSwitchCaseWithAbstractCase, |
| 443 | }; |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 444 | |
Ben Clayton | 22bd004 | 2022-05-31 20:40:59 +0000 | [diff] [blame] | 445 | /// Methods that do not materialize |
| 446 | constexpr Method kNoMaterializeMethods[] = { |
| 447 | Method::kPhonyAssign, |
Ben Clayton | aa037ac | 2022-06-29 19:07:30 +0000 | [diff] [blame] | 448 | // TODO(crbug.com/tint/1504): Enable once we have abstract overloads of builtins / binary |
| 449 | // ops: Method::kBuiltinArg, Method::kBinaryOp, |
Ben Clayton | 22bd004 | 2022-05-31 20:40:59 +0000 | [diff] [blame] | 450 | }; |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 451 | INSTANTIATE_TEST_SUITE_P( |
| 452 | MaterializeScalar, |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 453 | MaterializeAbstractNumericToConcreteType, |
| 454 | testing::Combine(testing::Values(Expectation::kMaterialize), |
| 455 | testing::ValuesIn(kScalarMethods), |
| 456 | testing::ValuesIn(std::vector<Data>{ |
Zhaoming Jiang | 6058882 | 2022-06-28 14:03:36 +0000 | [diff] [blame] | 457 | Types<i32, AInt>(0_a, 0.0), // |
| 458 | Types<i32, AInt>(1_a, 1.0), // |
| 459 | Types<i32, AInt>(-1_a, -1.0), // |
| 460 | Types<i32, AInt>(AInt(kHighestI32), kHighestI32), // |
| 461 | Types<i32, AInt>(AInt(kLowestI32), kLowestI32), // |
| 462 | Types<u32, AInt>(0_a, 0.0), // |
| 463 | Types<u32, AInt>(1_a, 1.0), // |
| 464 | Types<u32, AInt>(AInt(kHighestU32), kHighestU32), // |
| 465 | Types<u32, AInt>(AInt(kLowestU32), kLowestU32), // |
| 466 | Types<f32, AFloat>(0.0_a, 0.0), // |
| 467 | Types<f32, AFloat>(AFloat(kHighestF32), kHighestF32), // |
| 468 | Types<f32, AFloat>(AFloat(kLowestF32), kLowestF32), // |
| 469 | Types<f32, AFloat>(AFloat(kPiF32), kPiF64), // |
| 470 | Types<f32, AFloat>(AFloat(kSubnormalF32), kSubnormalF32), // |
| 471 | Types<f32, AFloat>(AFloat(-kSubnormalF32), -kSubnormalF32), // |
| 472 | /* Types<f16, AFloat>(0.0_a, 0.0), */ // |
| 473 | /* Types<f16, AFloat>(1.0_a, 1.0), */ // |
| 474 | /* Types<f16, AFloat>(AFloat(kHighestF16), kHighestF16), */ // |
| 475 | /* Types<f16, AFloat>(AFloat(kLowestF16), kLowestF16), */ // |
| 476 | /* Types<f16, AFloat>(AFloat(kPiF16), kPiF64), */ // |
| 477 | /* Types<f16, AFloat>(AFloat(kSubnormalF16), kSubnormalF16), */ // |
| 478 | /* Types<f16, AFloat>(AFloat(-kSubnormalF16), -kSubnormalF16), */ // |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 479 | }))); |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 480 | |
| 481 | INSTANTIATE_TEST_SUITE_P( |
| 482 | MaterializeVector, |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 483 | MaterializeAbstractNumericToConcreteType, |
| 484 | testing::Combine(testing::Values(Expectation::kMaterialize), |
| 485 | testing::ValuesIn(kVectorMethods), |
| 486 | testing::ValuesIn(std::vector<Data>{ |
Zhaoming Jiang | 6058882 | 2022-06-28 14:03:36 +0000 | [diff] [blame] | 487 | Types<i32V, AIntV>(0_a, 0.0), // |
| 488 | Types<i32V, AIntV>(1_a, 1.0), // |
| 489 | Types<i32V, AIntV>(-1_a, -1.0), // |
| 490 | Types<i32V, AIntV>(AInt(kHighestI32), kHighestI32), // |
| 491 | Types<i32V, AIntV>(AInt(kLowestI32), kLowestI32), // |
| 492 | Types<u32V, AIntV>(0_a, 0.0), // |
| 493 | Types<u32V, AIntV>(1_a, 1.0), // |
| 494 | Types<u32V, AIntV>(AInt(kHighestU32), kHighestU32), // |
| 495 | Types<u32V, AIntV>(AInt(kLowestU32), kLowestU32), // |
| 496 | Types<f32V, AFloatV>(0.0_a, 0.0), // |
| 497 | Types<f32V, AFloatV>(1.0_a, 1.0), // |
| 498 | Types<f32V, AFloatV>(-1.0_a, -1.0), // |
| 499 | Types<f32V, AFloatV>(AFloat(kHighestF32), kHighestF32), // |
| 500 | Types<f32V, AFloatV>(AFloat(kLowestF32), kLowestF32), // |
| 501 | Types<f32V, AFloatV>(AFloat(kPiF32), kPiF64), // |
| 502 | Types<f32V, AFloatV>(AFloat(kSubnormalF32), kSubnormalF32), // |
| 503 | Types<f32V, AFloatV>(AFloat(-kSubnormalF32), -kSubnormalF32), // |
| 504 | /* Types<f16V, AFloatV>(0.0_a, 0.0), */ // |
| 505 | /* Types<f16V, AFloatV>(1.0_a, 1.0), */ // |
| 506 | /* Types<f16V, AFloatV>(-1.0_a, -1.0), */ // |
| 507 | /* Types<f16V, AFloatV>(AFloat(kHighestF16), kHighestF16), */ // |
| 508 | /* Types<f16V, AFloatV>(AFloat(kLowestF16), kLowestF16), */ // |
| 509 | /* Types<f16V, AFloatV>(AFloat(kPiF16), kPiF64), */ // |
| 510 | /* Types<f16V, AFloatV>(AFloat(kSubnormalF16), kSubnormalF16), */ // |
| 511 | /* Types<f16V, AFloatV>(AFloat(-kSubnormalF16), -kSubnormalF16), */ // |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 512 | }))); |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 513 | |
| 514 | INSTANTIATE_TEST_SUITE_P( |
| 515 | MaterializeMatrix, |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 516 | MaterializeAbstractNumericToConcreteType, |
| 517 | testing::Combine(testing::Values(Expectation::kMaterialize), |
| 518 | testing::ValuesIn(kMatrixMethods), |
| 519 | testing::ValuesIn(std::vector<Data>{ |
Zhaoming Jiang | 6058882 | 2022-06-28 14:03:36 +0000 | [diff] [blame] | 520 | Types<f32M, AFloatM>(0.0_a, 0.0), // |
| 521 | Types<f32M, AFloatM>(1.0_a, 1.0), // |
| 522 | Types<f32M, AFloatM>(-1.0_a, -1.0), // |
| 523 | Types<f32M, AFloatM>(AFloat(kHighestF32), kHighestF32), // |
| 524 | Types<f32M, AFloatM>(AFloat(kLowestF32), kLowestF32), // |
| 525 | Types<f32M, AFloatM>(AFloat(kPiF32), kPiF64), // |
| 526 | Types<f32M, AFloatM>(AFloat(kSubnormalF32), kSubnormalF32), // |
| 527 | Types<f32M, AFloatM>(AFloat(-kSubnormalF32), -kSubnormalF32), // |
| 528 | /* Types<f16M, AFloatM>(0.0_a, 0.0), */ // |
| 529 | /* Types<f16M, AFloatM>(1.0_a, 1.0), */ // |
| 530 | /* Types<f16M, AFloatM>(-1.0_a, -1.0), */ // |
| 531 | /* Types<f16M, AFloatM>(AFloat(kHighestF16), kHighestF16), */ // |
| 532 | /* Types<f16M, AFloatM>(AFloat(kLowestF16), kLowestF16), */ // |
| 533 | /* Types<f16M, AFloatM>(AFloat(kPiF16), kPiF64), */ // |
| 534 | /* Types<f16M, AFloatM>(AFloat(kSubnormalF16), kSubnormalF16), */ // |
| 535 | /* Types<f16M, AFloatM>(AFloat(-kSubnormalF16), -kSubnormalF16), */ // |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 536 | }))); |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 537 | |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 538 | INSTANTIATE_TEST_SUITE_P(MaterializeSwitch, |
| 539 | MaterializeAbstractNumericToConcreteType, |
| 540 | testing::Combine(testing::Values(Expectation::kMaterialize), |
| 541 | testing::ValuesIn(kSwitchMethods), |
| 542 | testing::ValuesIn(std::vector<Data>{ |
| 543 | Types<i32, AInt>(0_a, 0.0), // |
| 544 | Types<i32, AInt>(1_a, 1.0), // |
| 545 | Types<i32, AInt>(-1_a, -1.0), // |
| 546 | Types<i32, AInt>(AInt(kHighestI32), kHighestI32), // |
| 547 | Types<i32, AInt>(AInt(kLowestI32), kLowestI32), // |
| 548 | Types<u32, AInt>(0_a, 0.0), // |
| 549 | Types<u32, AInt>(1_a, 1.0), // |
| 550 | Types<u32, AInt>(AInt(kHighestU32), kHighestU32), // |
| 551 | Types<u32, AInt>(AInt(kLowestU32), kLowestU32), // |
| 552 | }))); |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 553 | |
Ben Clayton | b8ac9339 | 2022-05-28 10:34:06 +0000 | [diff] [blame] | 554 | INSTANTIATE_TEST_SUITE_P(MaterializeWorkgroupSize, |
| 555 | MaterializeAbstractNumericToConcreteType, |
| 556 | testing::Combine(testing::Values(Expectation::kMaterialize), |
| 557 | testing::Values(Method::kWorkgroupSize), |
| 558 | testing::ValuesIn(std::vector<Data>{ |
| 559 | Types<i32, AInt>(1_a, 1.0), // |
| 560 | Types<i32, AInt>(10_a, 10.0), // |
| 561 | Types<i32, AInt>(65535_a, 65535.0), // |
| 562 | Types<u32, AInt>(1_a, 1.0), // |
| 563 | Types<u32, AInt>(10_a, 10.0), // |
| 564 | Types<u32, AInt>(65535_a, 65535.0), // |
| 565 | }))); |
| 566 | |
Ben Clayton | 22bd004 | 2022-05-31 20:40:59 +0000 | [diff] [blame] | 567 | INSTANTIATE_TEST_SUITE_P(NoMaterialize, |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 568 | MaterializeAbstractNumericToConcreteType, |
| 569 | testing::Combine(testing::Values(Expectation::kNoMaterialize), |
Ben Clayton | 22bd004 | 2022-05-31 20:40:59 +0000 | [diff] [blame] | 570 | testing::ValuesIn(kNoMaterializeMethods), |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 571 | testing::ValuesIn(std::vector<Data>{ |
Ben Clayton | 22bd004 | 2022-05-31 20:40:59 +0000 | [diff] [blame] | 572 | Types<AInt, AInt>(1_a, 1_a), // |
| 573 | Types<AIntV, AIntV>(1_a, 1_a), // |
| 574 | Types<AFloat, AFloat>(1.0_a, 1.0_a), // |
| 575 | Types<AFloatV, AFloatV>(1.0_a, 1.0_a), // |
| 576 | Types<AFloatM, AFloatM>(1.0_a, 1.0_a), // |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 577 | }))); |
Ben Clayton | 22bd004 | 2022-05-31 20:40:59 +0000 | [diff] [blame] | 578 | |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 579 | INSTANTIATE_TEST_SUITE_P(InvalidConversion, |
| 580 | MaterializeAbstractNumericToConcreteType, |
| 581 | testing::Combine(testing::Values(Expectation::kInvalidConversion), |
| 582 | testing::ValuesIn(kScalarMethods), |
| 583 | testing::ValuesIn(std::vector<Data>{ |
Ben Clayton | 22d8dea | 2022-06-20 19:23:02 +0000 | [diff] [blame] | 584 | Types<i32, AFloat>(), // |
| 585 | Types<u32, AFloat>(), // |
| 586 | Types<i32V, AFloatV>(), // |
| 587 | Types<u32V, AFloatV>(), // |
| 588 | Types<i32Varr, AInt>(), // |
| 589 | Types<i32Varr, AIntV>(), // |
| 590 | Types<i32Varr, AFloat>(), // |
| 591 | Types<i32Varr, AFloatV>(), // |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 592 | }))); |
| 593 | |
| 594 | INSTANTIATE_TEST_SUITE_P(ScalarValueCannotBeRepresented, |
| 595 | MaterializeAbstractNumericToConcreteType, |
| 596 | testing::Combine(testing::Values(Expectation::kValueCannotBeRepresented), |
| 597 | testing::ValuesIn(kScalarMethods), |
| 598 | testing::ValuesIn(std::vector<Data>{ |
Zhaoming Jiang | 6058882 | 2022-06-28 14:03:36 +0000 | [diff] [blame] | 599 | Types<i32, AInt>(0_a, kHighestI32 + 1), // |
| 600 | Types<i32, AInt>(0_a, kLowestI32 - 1), // |
| 601 | Types<u32, AInt>(0_a, kHighestU32 + 1), // |
| 602 | Types<u32, AInt>(0_a, kLowestU32 - 1), // |
| 603 | Types<f32, AFloat>(0.0_a, kTooBigF32), // |
| 604 | Types<f32, AFloat>(0.0_a, -kTooBigF32), // |
| 605 | /* Types<f16, AFloat>(0.0_a, kTooBigF16), */ // |
| 606 | /* Types<f16, AFloat>(0.0_a, -kTooBigF16), */ // |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 607 | }))); |
| 608 | |
| 609 | INSTANTIATE_TEST_SUITE_P(VectorValueCannotBeRepresented, |
| 610 | MaterializeAbstractNumericToConcreteType, |
| 611 | testing::Combine(testing::Values(Expectation::kValueCannotBeRepresented), |
| 612 | testing::ValuesIn(kVectorMethods), |
| 613 | testing::ValuesIn(std::vector<Data>{ |
Zhaoming Jiang | 6058882 | 2022-06-28 14:03:36 +0000 | [diff] [blame] | 614 | Types<i32V, AIntV>(0_a, kHighestI32 + 1), // |
| 615 | Types<i32V, AIntV>(0_a, kLowestI32 - 1), // |
| 616 | Types<u32V, AIntV>(0_a, kHighestU32 + 1), // |
| 617 | Types<u32V, AIntV>(0_a, kLowestU32 - 1), // |
| 618 | Types<f32V, AFloatV>(0.0_a, kTooBigF32), // |
| 619 | Types<f32V, AFloatV>(0.0_a, -kTooBigF32), // |
| 620 | /* Types<f16V, AFloatV>(0.0_a, kTooBigF16), */ // |
| 621 | /* Types<f16V, AFloatV>(0.0_a, -kTooBigF16), */ // |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 622 | }))); |
| 623 | |
| 624 | INSTANTIATE_TEST_SUITE_P(MatrixValueCannotBeRepresented, |
| 625 | MaterializeAbstractNumericToConcreteType, |
| 626 | testing::Combine(testing::Values(Expectation::kValueCannotBeRepresented), |
| 627 | testing::ValuesIn(kMatrixMethods), |
| 628 | testing::ValuesIn(std::vector<Data>{ |
Zhaoming Jiang | 6058882 | 2022-06-28 14:03:36 +0000 | [diff] [blame] | 629 | Types<f32M, AFloatM>(0.0_a, kTooBigF32), // |
| 630 | Types<f32M, AFloatM>(0.0_a, -kTooBigF32), // |
| 631 | /* Types<f16M, AFloatM>(0.0_a, kTooBigF16), */ // |
| 632 | /* Types<f16M, AFloatM>(0.0_a, -kTooBigF16), */ // |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 633 | }))); |
| 634 | |
| 635 | } // namespace materialize_abstract_numeric_to_concrete_type |
| 636 | |
| 637 | //////////////////////////////////////////////////////////////////////////////////////////////////// |
| 638 | // Tests that in the absence of a 'target type' an abstract-int will materialize to i32, and an |
| 639 | // abstract-float will materialize to f32. |
| 640 | //////////////////////////////////////////////////////////////////////////////////////////////////// |
| 641 | namespace materialize_abstract_numeric_to_default_type { |
| 642 | |
| 643 | // How should the materialization occur? |
| 644 | enum class Method { |
| 645 | // var a = abstract_expr; |
| 646 | kVar, |
| 647 | |
| 648 | // let a = abstract_expr; |
| 649 | kLet, |
| 650 | |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 651 | // min(abstract_expr, abstract_expr) |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 652 | kBuiltinArg, |
| 653 | |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 654 | // bitcast<f32>(abstract_expr) |
Ben Clayton | 8c7ffbd | 2022-05-28 07:09:17 +0000 | [diff] [blame] | 655 | kBitcastF32Arg, |
| 656 | |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 657 | // bitcast<vec3<f32>>(abstract_expr) |
Ben Clayton | 8c7ffbd | 2022-05-28 07:09:17 +0000 | [diff] [blame] | 658 | kBitcastVec3F32Arg, |
| 659 | |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 660 | // array<i32, abstract_expr>() |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 661 | kArrayLength, |
| 662 | |
| 663 | // switch (abstract_expr) { |
| 664 | // case abstract_expr: {} |
| 665 | // default: {} |
| 666 | // } |
| 667 | kSwitch, |
Ben Clayton | b8ac9339 | 2022-05-28 10:34:06 +0000 | [diff] [blame] | 668 | |
| 669 | // @workgroup_size(abstract_expr) |
dan sinclair | b29892b | 2022-06-07 13:55:34 +0000 | [diff] [blame] | 670 | // @compute |
Ben Clayton | b8ac9339 | 2022-05-28 10:34:06 +0000 | [diff] [blame] | 671 | // fn f() {} |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 672 | kWorkgroupSize, |
| 673 | |
| 674 | // arr[abstract_expr] |
| 675 | kIndex, |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 676 | }; |
| 677 | |
| 678 | static std::ostream& operator<<(std::ostream& o, Method m) { |
| 679 | switch (m) { |
| 680 | case Method::kVar: |
| 681 | return o << "var"; |
| 682 | case Method::kLet: |
| 683 | return o << "let"; |
| 684 | case Method::kBuiltinArg: |
| 685 | return o << "builtin-arg"; |
Ben Clayton | 8c7ffbd | 2022-05-28 07:09:17 +0000 | [diff] [blame] | 686 | case Method::kBitcastF32Arg: |
| 687 | return o << "bitcast-f32-arg"; |
| 688 | case Method::kBitcastVec3F32Arg: |
| 689 | return o << "bitcast-vec3-f32-arg"; |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 690 | case Method::kArrayLength: |
| 691 | return o << "array-length"; |
| 692 | case Method::kSwitch: |
| 693 | return o << "switch"; |
Ben Clayton | b8ac9339 | 2022-05-28 10:34:06 +0000 | [diff] [blame] | 694 | case Method::kWorkgroupSize: |
| 695 | return o << "workgroup-size"; |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 696 | case Method::kIndex: |
| 697 | return o << "index"; |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 698 | } |
| 699 | return o << "<unknown>"; |
| 700 | } |
| 701 | |
| 702 | struct Data { |
| 703 | std::string expected_type_name; |
| 704 | std::string expected_element_type_name; |
| 705 | builder::sem_type_func_ptr expected_sem_ty; |
| 706 | std::string abstract_type_name; |
| 707 | builder::ast_expr_func_ptr abstract_expr; |
| 708 | std::variant<AInt, AFloat> materialized_value; |
| 709 | double literal_value; |
| 710 | }; |
| 711 | |
| 712 | template <typename EXPECTED_TYPE, typename ABSTRACT_TYPE, typename MATERIALIZED_TYPE> |
| 713 | Data Types(MATERIALIZED_TYPE materialized_value, double literal_value) { |
| 714 | using ExpectedDataType = builder::DataType<EXPECTED_TYPE>; |
| 715 | using AbstractDataType = builder::DataType<ABSTRACT_TYPE>; |
| 716 | using TargetElementDataType = builder::DataType<typename ExpectedDataType::ElementType>; |
| 717 | return { |
| 718 | ExpectedDataType::Name(), // expected_type_name |
| 719 | TargetElementDataType::Name(), // expected_element_type_name |
| 720 | ExpectedDataType::Sem, // expected_sem_ty |
| 721 | AbstractDataType::Name(), // abstract_type_name |
| 722 | AbstractDataType::Expr, // abstract_expr |
| 723 | materialized_value, |
| 724 | literal_value, |
| 725 | }; |
| 726 | } |
| 727 | |
| 728 | static std::ostream& operator<<(std::ostream& o, const Data& c) { |
| 729 | auto print_value = [&](auto&& v) { o << v; }; |
| 730 | o << "[" << c.expected_type_name << " <- " << c.abstract_type_name << "] ["; |
| 731 | std::visit(print_value, c.materialized_value); |
| 732 | o << " <- " << c.literal_value << "]"; |
| 733 | return o; |
| 734 | } |
| 735 | |
| 736 | using MaterializeAbstractNumericToDefaultType = |
Ben Clayton | aa037ac | 2022-06-29 19:07:30 +0000 | [diff] [blame] | 737 | MaterializeTest<std::tuple<Expectation, Method, Data>>; |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 738 | |
| 739 | TEST_P(MaterializeAbstractNumericToDefaultType, Test) { |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 740 | const auto& param = GetParam(); |
| 741 | const auto& expectation = std::get<0>(param); |
| 742 | const auto& method = std::get<1>(param); |
| 743 | const auto& data = std::get<2>(param); |
| 744 | |
| 745 | ast::ExpressionList abstract_exprs; |
| 746 | auto abstract_expr = [&] { |
| 747 | auto* expr = data.abstract_expr(*this, data.literal_value); |
| 748 | abstract_exprs.emplace_back(expr); |
| 749 | return expr; |
| 750 | }; |
| 751 | switch (method) { |
| 752 | case Method::kVar: |
| 753 | WrapInFunction(Decl(Var("a", nullptr, abstract_expr()))); |
| 754 | break; |
| 755 | case Method::kLet: |
| 756 | WrapInFunction(Decl(Let("a", nullptr, abstract_expr()))); |
| 757 | break; |
| 758 | case Method::kBuiltinArg: |
| 759 | WrapInFunction(CallStmt(Call("min", abstract_expr(), abstract_expr()))); |
| 760 | break; |
Ben Clayton | 8c7ffbd | 2022-05-28 07:09:17 +0000 | [diff] [blame] | 761 | case Method::kBitcastF32Arg: |
| 762 | WrapInFunction(Bitcast<f32>(abstract_expr())); |
| 763 | break; |
| 764 | case Method::kBitcastVec3F32Arg: |
| 765 | WrapInFunction(Bitcast(ty.vec3<f32>(), abstract_expr())); |
| 766 | break; |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 767 | case Method::kArrayLength: |
| 768 | WrapInFunction(Construct(ty.array(ty.i32(), abstract_expr()))); |
| 769 | break; |
| 770 | case Method::kSwitch: |
| 771 | WrapInFunction(Switch(abstract_expr(), |
| 772 | Case(abstract_expr()->As<ast::IntLiteralExpression>()), |
| 773 | DefaultCase())); |
| 774 | break; |
Ben Clayton | b8ac9339 | 2022-05-28 10:34:06 +0000 | [diff] [blame] | 775 | case Method::kWorkgroupSize: |
| 776 | Func("f", {}, ty.void_(), {}, |
| 777 | {WorkgroupSize(abstract_expr()), Stage(ast::PipelineStage::kCompute)}); |
| 778 | break; |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 779 | case Method::kIndex: |
Ben Clayton | 01208e7 | 2022-06-25 08:12:59 +0000 | [diff] [blame] | 780 | GlobalVar("arr", ty.array<i32, 4>(), ast::StorageClass::kPrivate); |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 781 | WrapInFunction(IndexAccessor("arr", abstract_expr())); |
| 782 | break; |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 783 | } |
| 784 | |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 785 | switch (expectation) { |
| 786 | case Expectation::kMaterialize: { |
| 787 | ASSERT_TRUE(r()->Resolve()) << r()->error(); |
| 788 | for (auto* expr : abstract_exprs) { |
| 789 | auto* materialize = Sem().Get<sem::Materialize>(expr); |
| 790 | ASSERT_NE(materialize, nullptr); |
Ben Clayton | aa037ac | 2022-06-29 19:07:30 +0000 | [diff] [blame] | 791 | CheckTypesAndValues(materialize, data.expected_sem_ty(*this), |
| 792 | data.materialized_value); |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 793 | } |
| 794 | break; |
| 795 | } |
| 796 | case Expectation::kInvalidConversion: { |
| 797 | ASSERT_FALSE(r()->Resolve()); |
| 798 | std::string expect; |
| 799 | switch (method) { |
| 800 | case Method::kBuiltinArg: |
| 801 | expect = "error: no matching call to min(" + data.abstract_type_name + ", " + |
| 802 | data.abstract_type_name + ")"; |
| 803 | break; |
| 804 | default: |
| 805 | expect = "error: cannot convert value of type '" + data.abstract_type_name + |
| 806 | "' to type '" + data.expected_type_name + "'"; |
| 807 | break; |
| 808 | } |
| 809 | EXPECT_THAT(r()->error(), testing::StartsWith(expect)); |
| 810 | break; |
| 811 | } |
| 812 | case Expectation::kValueCannotBeRepresented: |
| 813 | ASSERT_FALSE(r()->Resolve()); |
| 814 | EXPECT_THAT(r()->error(), testing::HasSubstr("cannot be represented as '" + |
| 815 | data.expected_element_type_name + "'")); |
| 816 | break; |
| 817 | default: |
| 818 | FAIL() << "unhandled expectation: " << expectation; |
| 819 | } |
| 820 | } |
| 821 | |
| 822 | /// Methods that support scalar materialization |
| 823 | constexpr Method kScalarMethods[] = { |
| 824 | Method::kLet, |
| 825 | Method::kVar, |
| 826 | Method::kBuiltinArg, |
Ben Clayton | 8c7ffbd | 2022-05-28 07:09:17 +0000 | [diff] [blame] | 827 | Method::kBitcastF32Arg, |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 828 | }; |
| 829 | |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 830 | /// Methods that support abstract-integer materialization |
Ben Clayton | 649d3d9 | 2022-05-31 18:11:34 +0000 | [diff] [blame] | 831 | /// Note: Doesn't contain kWorkgroupSize or kArrayLength as they have tighter constraints on the |
| 832 | /// range of allowed integer values. |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 833 | constexpr Method kAIntMethods[] = { |
| 834 | Method::kSwitch, |
| 835 | Method::kIndex, |
| 836 | }; |
| 837 | |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 838 | /// Methods that support vector materialization |
| 839 | constexpr Method kVectorMethods[] = { |
| 840 | Method::kLet, |
| 841 | Method::kVar, |
| 842 | Method::kBuiltinArg, |
Ben Clayton | 8c7ffbd | 2022-05-28 07:09:17 +0000 | [diff] [blame] | 843 | Method::kBitcastVec3F32Arg, |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 844 | }; |
| 845 | |
| 846 | /// Methods that support matrix materialization |
| 847 | constexpr Method kMatrixMethods[] = { |
| 848 | Method::kLet, |
| 849 | Method::kVar, |
| 850 | }; |
| 851 | |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 852 | INSTANTIATE_TEST_SUITE_P( |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 853 | MaterializeScalar, |
| 854 | MaterializeAbstractNumericToDefaultType, |
| 855 | testing::Combine(testing::Values(Expectation::kMaterialize), |
| 856 | testing::ValuesIn(kScalarMethods), |
| 857 | testing::ValuesIn(std::vector<Data>{ |
| 858 | Types<i32, AInt>(0_a, 0.0), // |
| 859 | Types<i32, AInt>(1_a, 1.0), // |
| 860 | Types<i32, AInt>(-1_a, -1.0), // |
| 861 | Types<i32, AInt>(AInt(kHighestI32), kHighestI32), // |
| 862 | Types<i32, AInt>(AInt(kLowestI32), kLowestI32), // |
| 863 | Types<f32, AFloat>(0.0_a, 0.0), // |
| 864 | Types<f32, AFloat>(AFloat(kHighestF32), kHighestF32), // |
| 865 | Types<f32, AFloat>(AFloat(kLowestF32), kLowestF32), // |
| 866 | Types<f32, AFloat>(AFloat(kPiF32), kPiF64), // |
| 867 | Types<f32, AFloat>(AFloat(kSubnormalF32), kSubnormalF32), // |
| 868 | Types<f32, AFloat>(AFloat(-kSubnormalF32), -kSubnormalF32), // |
| 869 | }))); |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 870 | |
| 871 | INSTANTIATE_TEST_SUITE_P( |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 872 | MaterializeVector, |
| 873 | MaterializeAbstractNumericToDefaultType, |
| 874 | testing::Combine(testing::Values(Expectation::kMaterialize), |
| 875 | testing::ValuesIn(kVectorMethods), |
| 876 | testing::ValuesIn(std::vector<Data>{ |
| 877 | Types<i32V, AIntV>(0_a, 0.0), // |
| 878 | Types<i32V, AIntV>(1_a, 1.0), // |
| 879 | Types<i32V, AIntV>(-1_a, -1.0), // |
| 880 | Types<i32V, AIntV>(AInt(kHighestI32), kHighestI32), // |
| 881 | Types<i32V, AIntV>(AInt(kLowestI32), kLowestI32), // |
| 882 | Types<f32V, AFloatV>(0.0_a, 0.0), // |
| 883 | Types<f32V, AFloatV>(1.0_a, 1.0), // |
| 884 | Types<f32V, AFloatV>(-1.0_a, -1.0), // |
| 885 | Types<f32V, AFloatV>(AFloat(kHighestF32), kHighestF32), // |
| 886 | Types<f32V, AFloatV>(AFloat(kLowestF32), kLowestF32), // |
| 887 | Types<f32V, AFloatV>(AFloat(kPiF32), kPiF64), // |
| 888 | Types<f32V, AFloatV>(AFloat(kSubnormalF32), kSubnormalF32), // |
| 889 | Types<f32V, AFloatV>(AFloat(-kSubnormalF32), -kSubnormalF32), // |
| 890 | }))); |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 891 | |
| 892 | INSTANTIATE_TEST_SUITE_P( |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 893 | MaterializeMatrix, |
| 894 | MaterializeAbstractNumericToDefaultType, |
| 895 | testing::Combine(testing::Values(Expectation::kMaterialize), |
| 896 | testing::ValuesIn(kMatrixMethods), |
| 897 | testing::ValuesIn(std::vector<Data>{ |
| 898 | Types<f32M, AFloatM>(0.0_a, 0.0), // |
| 899 | Types<f32M, AFloatM>(1.0_a, 1.0), // |
| 900 | Types<f32M, AFloatM>(-1.0_a, -1.0), // |
| 901 | Types<f32M, AFloatM>(AFloat(kHighestF32), kHighestF32), // |
| 902 | Types<f32M, AFloatM>(AFloat(kLowestF32), kLowestF32), // |
| 903 | Types<f32M, AFloatM>(AFloat(kPiF32), kPiF64), // |
| 904 | Types<f32M, AFloatM>(AFloat(kSubnormalF32), kSubnormalF32), // |
| 905 | Types<f32M, AFloatM>(AFloat(-kSubnormalF32), -kSubnormalF32), // |
| 906 | }))); |
Ben Clayton | e34e059 | 2022-05-25 21:16:55 +0000 | [diff] [blame] | 907 | |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 908 | INSTANTIATE_TEST_SUITE_P(MaterializeAInt, |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 909 | MaterializeAbstractNumericToDefaultType, |
| 910 | testing::Combine(testing::Values(Expectation::kMaterialize), |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 911 | testing::ValuesIn(kAIntMethods), |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 912 | testing::ValuesIn(std::vector<Data>{ |
| 913 | Types<i32, AInt>(0_a, 0.0), // |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 914 | Types<i32, AInt>(10_a, 10.0), // |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 915 | Types<i32, AInt>(AInt(kHighestI32), kHighestI32), // |
| 916 | Types<i32, AInt>(AInt(kLowestI32), kLowestI32), // |
| 917 | }))); |
| 918 | |
Ben Clayton | 649d3d9 | 2022-05-31 18:11:34 +0000 | [diff] [blame] | 919 | INSTANTIATE_TEST_SUITE_P( |
| 920 | MaterializeArrayLength, |
| 921 | MaterializeAbstractNumericToDefaultType, |
| 922 | testing::Combine(testing::Values(Expectation::kMaterialize), |
| 923 | testing::Values(Method::kArrayLength), |
| 924 | testing::ValuesIn(std::vector<Data>{ |
| 925 | Types<i32, AInt>(1_a, 1.0), // |
| 926 | Types<i32, AInt>(10_a, 10.0), // |
| 927 | Types<i32, AInt>(1000_a, 1000.0), // |
| 928 | // Note: kHighestI32 cannot be used due to max-byte-size validation |
| 929 | }))); |
| 930 | |
Ben Clayton | b8ac9339 | 2022-05-28 10:34:06 +0000 | [diff] [blame] | 931 | INSTANTIATE_TEST_SUITE_P(MaterializeWorkgroupSize, |
| 932 | MaterializeAbstractNumericToDefaultType, |
| 933 | testing::Combine(testing::Values(Expectation::kMaterialize), |
| 934 | testing::Values(Method::kWorkgroupSize), |
| 935 | testing::ValuesIn(std::vector<Data>{ |
| 936 | Types<i32, AInt>(1_a, 1.0), // |
| 937 | Types<i32, AInt>(10_a, 10.0), // |
| 938 | Types<i32, AInt>(65535_a, 65535.0), // |
| 939 | }))); |
| 940 | |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 941 | INSTANTIATE_TEST_SUITE_P(ScalarValueCannotBeRepresented, |
| 942 | MaterializeAbstractNumericToDefaultType, |
| 943 | testing::Combine(testing::Values(Expectation::kValueCannotBeRepresented), |
| 944 | testing::ValuesIn(kScalarMethods), |
| 945 | testing::ValuesIn(std::vector<Data>{ |
| 946 | Types<i32, AInt>(0_a, kHighestI32 + 1), // |
| 947 | Types<i32, AInt>(0_a, kLowestI32 - 1), // |
| 948 | Types<f32, AFloat>(0.0_a, kTooBigF32), // |
| 949 | Types<f32, AFloat>(0.0_a, -kTooBigF32), // |
| 950 | }))); |
| 951 | |
| 952 | INSTANTIATE_TEST_SUITE_P(VectorValueCannotBeRepresented, |
| 953 | MaterializeAbstractNumericToDefaultType, |
| 954 | testing::Combine(testing::Values(Expectation::kValueCannotBeRepresented), |
| 955 | testing::ValuesIn(kVectorMethods), |
| 956 | testing::ValuesIn(std::vector<Data>{ |
| 957 | Types<i32V, AIntV>(0_a, kHighestI32 + 1), // |
| 958 | Types<i32V, AIntV>(0_a, kLowestI32 - 1), // |
| 959 | Types<i32V, AIntV>(0_a, kHighestU32 + 1), // |
| 960 | Types<f32V, AFloatV>(0.0_a, kTooBigF32), // |
| 961 | Types<f32V, AFloatV>(0.0_a, -kTooBigF32), // |
| 962 | }))); |
| 963 | |
| 964 | INSTANTIATE_TEST_SUITE_P(MatrixValueCannotBeRepresented, |
| 965 | MaterializeAbstractNumericToDefaultType, |
| 966 | testing::Combine(testing::Values(Expectation::kValueCannotBeRepresented), |
| 967 | testing::ValuesIn(kMatrixMethods), |
| 968 | testing::ValuesIn(std::vector<Data>{ |
| 969 | Types<f32M, AFloatM>(0.0_a, kTooBigF32), // |
| 970 | Types<f32M, AFloatM>(0.0_a, -kTooBigF32), // |
| 971 | }))); |
| 972 | |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 973 | INSTANTIATE_TEST_SUITE_P(AIntValueCannotBeRepresented, |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 974 | MaterializeAbstractNumericToDefaultType, |
| 975 | testing::Combine(testing::Values(Expectation::kValueCannotBeRepresented), |
Ben Clayton | 49a0914 | 2022-05-31 15:22:21 +0000 | [diff] [blame] | 976 | testing::ValuesIn(kAIntMethods), |
Ben Clayton | b8ac9339 | 2022-05-28 10:34:06 +0000 | [diff] [blame] | 977 | testing::ValuesIn(std::vector<Data>{ |
| 978 | Types<i32, AInt>(0_a, kHighestI32 + 1), // |
| 979 | Types<i32, AInt>(0_a, kLowestI32 - 1), // |
| 980 | }))); |
| 981 | |
| 982 | INSTANTIATE_TEST_SUITE_P(WorkgroupSizeValueCannotBeRepresented, |
| 983 | MaterializeAbstractNumericToDefaultType, |
| 984 | testing::Combine(testing::Values(Expectation::kValueCannotBeRepresented), |
| 985 | testing::Values(Method::kWorkgroupSize), |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 986 | testing::ValuesIn(std::vector<Data>{ |
| 987 | Types<i32, AInt>(0_a, kHighestI32 + 1), // |
| 988 | Types<i32, AInt>(0_a, kLowestI32 - 1), // |
| 989 | }))); |
| 990 | |
Ben Clayton | 649d3d9 | 2022-05-31 18:11:34 +0000 | [diff] [blame] | 991 | INSTANTIATE_TEST_SUITE_P(ArrayLengthValueCannotBeRepresented, |
| 992 | MaterializeAbstractNumericToDefaultType, |
| 993 | testing::Combine(testing::Values(Expectation::kValueCannotBeRepresented), |
| 994 | testing::Values(Method::kArrayLength), |
| 995 | testing::ValuesIn(std::vector<Data>{ |
| 996 | Types<i32, AInt>(0_a, kHighestI32 + 1), // |
| 997 | }))); |
| 998 | |
Ben Clayton | 3a236c6 | 2022-05-28 05:28:11 +0000 | [diff] [blame] | 999 | } // namespace materialize_abstract_numeric_to_default_type |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 1000 | |
Ben Clayton | 22d8dea | 2022-06-20 19:23:02 +0000 | [diff] [blame] | 1001 | using MaterializeAbstractNumericToUnrelatedType = resolver::ResolverTest; |
| 1002 | |
| 1003 | TEST_F(MaterializeAbstractNumericToUnrelatedType, AIntToStructVarCtor) { |
| 1004 | Structure("S", {Member("a", ty.i32())}); |
| 1005 | WrapInFunction(Decl(Var("v", ty.type_name("S"), Expr(Source{{12, 34}}, 1_a)))); |
| 1006 | ASSERT_FALSE(r()->Resolve()); |
| 1007 | EXPECT_THAT( |
| 1008 | r()->error(), |
| 1009 | testing::HasSubstr("error: cannot convert value of type 'abstract-int' to type 'S'")); |
| 1010 | } |
| 1011 | |
| 1012 | TEST_F(MaterializeAbstractNumericToUnrelatedType, AIntToStructLetCtor) { |
| 1013 | Structure("S", {Member("a", ty.i32())}); |
| 1014 | WrapInFunction(Decl(Let("v", ty.type_name("S"), Expr(Source{{12, 34}}, 1_a)))); |
| 1015 | ASSERT_FALSE(r()->Resolve()); |
| 1016 | EXPECT_THAT( |
| 1017 | r()->error(), |
| 1018 | testing::HasSubstr("error: cannot convert value of type 'abstract-int' to type 'S'")); |
| 1019 | } |
| 1020 | |
Ben Clayton | 932418e | 2022-05-24 21:42:03 +0000 | [diff] [blame] | 1021 | } // namespace |
| 1022 | } // namespace tint::resolver |