OLD | NEW |
1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "src/compiler/machine-operator.h" | 5 #include "src/compiler/machine-operator.h" |
6 | 6 |
7 #include "src/base/lazy-instance.h" | 7 #include "src/base/lazy-instance.h" |
8 #include "src/compiler/opcodes.h" | 8 #include "src/compiler/opcodes.h" |
9 #include "src/compiler/operator.h" | 9 #include "src/compiler/operator.h" |
10 | 10 |
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
61 return base::hash_combine(rep.machine_type(), rep.write_barrier_kind()); | 61 return base::hash_combine(rep.machine_type(), rep.write_barrier_kind()); |
62 } | 62 } |
63 | 63 |
64 | 64 |
65 std::ostream& operator<<(std::ostream& os, StoreRepresentation rep) { | 65 std::ostream& operator<<(std::ostream& os, StoreRepresentation rep) { |
66 return os << "(" << rep.machine_type() << " : " << rep.write_barrier_kind() | 66 return os << "(" << rep.machine_type() << " : " << rep.write_barrier_kind() |
67 << ")"; | 67 << ")"; |
68 } | 68 } |
69 | 69 |
70 | 70 |
| 71 LoadRepresentation LoadRepresentationOf(Operator const* op) { |
| 72 DCHECK_EQ(IrOpcode::kLoad, op->opcode()); |
| 73 return OpParameter<LoadRepresentation>(op); |
| 74 } |
| 75 |
| 76 |
71 StoreRepresentation const& StoreRepresentationOf(Operator const* op) { | 77 StoreRepresentation const& StoreRepresentationOf(Operator const* op) { |
72 DCHECK_EQ(IrOpcode::kStore, op->opcode()); | 78 DCHECK_EQ(IrOpcode::kStore, op->opcode()); |
73 return OpParameter<StoreRepresentation>(op); | 79 return OpParameter<StoreRepresentation>(op); |
74 } | 80 } |
75 | 81 |
76 | 82 |
77 CheckedLoadRepresentation CheckedLoadRepresentationOf(Operator const* op) { | 83 CheckedLoadRepresentation CheckedLoadRepresentationOf(Operator const* op) { |
78 DCHECK_EQ(IrOpcode::kCheckedLoad, op->opcode()); | 84 DCHECK_EQ(IrOpcode::kCheckedLoad, op->opcode()); |
79 return OpParameter<CheckedLoadRepresentation>(op); | 85 return OpParameter<CheckedLoadRepresentation>(op); |
80 } | 86 } |
(...skipping 112 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
193 V(Float32RoundUp, Operator::kNoProperties, 1, 0, 1) \ | 199 V(Float32RoundUp, Operator::kNoProperties, 1, 0, 1) \ |
194 V(Float64RoundUp, Operator::kNoProperties, 1, 0, 1) \ | 200 V(Float64RoundUp, Operator::kNoProperties, 1, 0, 1) \ |
195 V(Float32RoundTruncate, Operator::kNoProperties, 1, 0, 1) \ | 201 V(Float32RoundTruncate, Operator::kNoProperties, 1, 0, 1) \ |
196 V(Float64RoundTruncate, Operator::kNoProperties, 1, 0, 1) \ | 202 V(Float64RoundTruncate, Operator::kNoProperties, 1, 0, 1) \ |
197 V(Float64RoundTiesAway, Operator::kNoProperties, 1, 0, 1) \ | 203 V(Float64RoundTiesAway, Operator::kNoProperties, 1, 0, 1) \ |
198 V(Float32RoundTiesEven, Operator::kNoProperties, 1, 0, 1) \ | 204 V(Float32RoundTiesEven, Operator::kNoProperties, 1, 0, 1) \ |
199 V(Float64RoundTiesEven, Operator::kNoProperties, 1, 0, 1) | 205 V(Float64RoundTiesEven, Operator::kNoProperties, 1, 0, 1) |
200 | 206 |
201 | 207 |
202 #define MACHINE_TYPE_LIST(V) \ | 208 #define MACHINE_TYPE_LIST(V) \ |
203 V(MachFloat32) \ | 209 V(Float32) \ |
204 V(MachFloat64) \ | 210 V(Float64) \ |
205 V(MachInt8) \ | 211 V(Int8) \ |
206 V(MachUint8) \ | 212 V(Uint8) \ |
207 V(MachInt16) \ | 213 V(Int16) \ |
208 V(MachUint16) \ | 214 V(Uint16) \ |
209 V(MachInt32) \ | 215 V(Int32) \ |
210 V(MachUint32) \ | 216 V(Uint32) \ |
211 V(MachInt64) \ | 217 V(Int64) \ |
212 V(MachUint64) \ | 218 V(Uint64) \ |
213 V(MachPtr) \ | 219 V(Pointer) \ |
214 V(MachAnyTagged) | 220 V(AnyTagged) |
215 | 221 |
216 | 222 |
217 struct MachineOperatorGlobalCache { | 223 struct MachineOperatorGlobalCache { |
218 #define PURE(Name, properties, value_input_count, control_input_count, \ | 224 #define PURE(Name, properties, value_input_count, control_input_count, \ |
219 output_count) \ | 225 output_count) \ |
220 struct Name##Operator final : public Operator { \ | 226 struct Name##Operator final : public Operator { \ |
221 Name##Operator() \ | 227 Name##Operator() \ |
222 : Operator(IrOpcode::k##Name, Operator::kPure | properties, #Name, \ | 228 : Operator(IrOpcode::k##Name, Operator::kPure | properties, #Name, \ |
223 value_input_count, 0, control_input_count, output_count, 0, \ | 229 value_input_count, 0, control_input_count, output_count, 0, \ |
224 0) {} \ | 230 0) {} \ |
(...skipping 14 matching lines...) Expand all Loading... |
239 TruncateFloat64ToInt32Operator<TruncationMode::kJavaScript> | 245 TruncateFloat64ToInt32Operator<TruncationMode::kJavaScript> |
240 kTruncateFloat64ToInt32JavaScript; | 246 kTruncateFloat64ToInt32JavaScript; |
241 TruncateFloat64ToInt32Operator<TruncationMode::kRoundToZero> | 247 TruncateFloat64ToInt32Operator<TruncationMode::kRoundToZero> |
242 kTruncateFloat64ToInt32RoundToZero; | 248 kTruncateFloat64ToInt32RoundToZero; |
243 | 249 |
244 #define LOAD(Type) \ | 250 #define LOAD(Type) \ |
245 struct Load##Type##Operator final : public Operator1<LoadRepresentation> { \ | 251 struct Load##Type##Operator final : public Operator1<LoadRepresentation> { \ |
246 Load##Type##Operator() \ | 252 Load##Type##Operator() \ |
247 : Operator1<LoadRepresentation>( \ | 253 : Operator1<LoadRepresentation>( \ |
248 IrOpcode::kLoad, Operator::kNoThrow | Operator::kNoWrite, \ | 254 IrOpcode::kLoad, Operator::kNoThrow | Operator::kNoWrite, \ |
249 "Load", 2, 1, 1, 1, 1, 0, k##Type) {} \ | 255 "Load", 2, 1, 1, 1, 1, 0, MachineType::Type()) {} \ |
250 }; \ | 256 }; \ |
251 struct CheckedLoad##Type##Operator final \ | 257 struct CheckedLoad##Type##Operator final \ |
252 : public Operator1<CheckedLoadRepresentation> { \ | 258 : public Operator1<CheckedLoadRepresentation> { \ |
253 CheckedLoad##Type##Operator() \ | 259 CheckedLoad##Type##Operator() \ |
254 : Operator1<CheckedLoadRepresentation>( \ | 260 : Operator1<CheckedLoadRepresentation>( \ |
255 IrOpcode::kCheckedLoad, Operator::kNoThrow | Operator::kNoWrite, \ | 261 IrOpcode::kCheckedLoad, Operator::kNoThrow | Operator::kNoWrite, \ |
256 "CheckedLoad", 3, 1, 1, 1, 1, 0, k##Type) {} \ | 262 "CheckedLoad", 3, 1, 1, 1, 1, 0, MachineType::Type()) {} \ |
257 }; \ | 263 }; \ |
258 Load##Type##Operator kLoad##Type; \ | 264 Load##Type##Operator kLoad##Type; \ |
259 CheckedLoad##Type##Operator kCheckedLoad##Type; | 265 CheckedLoad##Type##Operator kCheckedLoad##Type; |
260 MACHINE_TYPE_LIST(LOAD) | 266 MACHINE_TYPE_LIST(LOAD) |
261 #undef LOAD | 267 #undef LOAD |
262 | 268 |
263 #define STORE(Type) \ | 269 #define STORE(Type) \ |
264 struct Store##Type##Operator : public Operator1<StoreRepresentation> { \ | 270 struct Store##Type##Operator : public Operator1<StoreRepresentation> { \ |
265 explicit Store##Type##Operator(WriteBarrierKind write_barrier_kind) \ | 271 explicit Store##Type##Operator(WriteBarrierKind write_barrier_kind) \ |
266 : Operator1<StoreRepresentation>( \ | 272 : Operator1<StoreRepresentation>( \ |
267 IrOpcode::kStore, Operator::kNoRead | Operator::kNoThrow, \ | 273 IrOpcode::kStore, Operator::kNoRead | Operator::kNoThrow, \ |
268 "Store", 3, 1, 1, 0, 1, 0, \ | 274 "Store", 3, 1, 1, 0, 1, 0, \ |
269 StoreRepresentation(k##Type, write_barrier_kind)) {} \ | 275 StoreRepresentation(MachineType::Type(), write_barrier_kind)) {} \ |
270 }; \ | 276 }; \ |
271 struct Store##Type##NoWriteBarrier##Operator final \ | 277 struct Store##Type##NoWriteBarrier##Operator final \ |
272 : public Store##Type##Operator { \ | 278 : public Store##Type##Operator { \ |
273 Store##Type##NoWriteBarrier##Operator() \ | 279 Store##Type##NoWriteBarrier##Operator() \ |
274 : Store##Type##Operator(kNoWriteBarrier) {} \ | 280 : Store##Type##Operator(kNoWriteBarrier) {} \ |
275 }; \ | 281 }; \ |
276 struct Store##Type##MapWriteBarrier##Operator final \ | 282 struct Store##Type##MapWriteBarrier##Operator final \ |
277 : public Store##Type##Operator { \ | 283 : public Store##Type##Operator { \ |
278 Store##Type##MapWriteBarrier##Operator() \ | 284 Store##Type##MapWriteBarrier##Operator() \ |
279 : Store##Type##Operator(kMapWriteBarrier) {} \ | 285 : Store##Type##Operator(kMapWriteBarrier) {} \ |
280 }; \ | 286 }; \ |
281 struct Store##Type##PointerWriteBarrier##Operator final \ | 287 struct Store##Type##PointerWriteBarrier##Operator final \ |
282 : public Store##Type##Operator { \ | 288 : public Store##Type##Operator { \ |
283 Store##Type##PointerWriteBarrier##Operator() \ | 289 Store##Type##PointerWriteBarrier##Operator() \ |
284 : Store##Type##Operator(kPointerWriteBarrier) {} \ | 290 : Store##Type##Operator(kPointerWriteBarrier) {} \ |
285 }; \ | 291 }; \ |
286 struct Store##Type##FullWriteBarrier##Operator final \ | 292 struct Store##Type##FullWriteBarrier##Operator final \ |
287 : public Store##Type##Operator { \ | 293 : public Store##Type##Operator { \ |
288 Store##Type##FullWriteBarrier##Operator() \ | 294 Store##Type##FullWriteBarrier##Operator() \ |
289 : Store##Type##Operator(kFullWriteBarrier) {} \ | 295 : Store##Type##Operator(kFullWriteBarrier) {} \ |
290 }; \ | 296 }; \ |
291 struct CheckedStore##Type##Operator final \ | 297 struct CheckedStore##Type##Operator final \ |
292 : public Operator1<CheckedStoreRepresentation> { \ | 298 : public Operator1<CheckedStoreRepresentation> { \ |
293 CheckedStore##Type##Operator() \ | 299 CheckedStore##Type##Operator() \ |
294 : Operator1<CheckedStoreRepresentation>( \ | 300 : Operator1<CheckedStoreRepresentation>( \ |
295 IrOpcode::kCheckedStore, Operator::kNoRead | Operator::kNoThrow, \ | 301 IrOpcode::kCheckedStore, Operator::kNoRead | Operator::kNoThrow, \ |
296 "CheckedStore", 4, 1, 1, 0, 1, 0, k##Type) {} \ | 302 "CheckedStore", 4, 1, 1, 0, 1, 0, MachineType::Type()) {} \ |
297 }; \ | 303 }; \ |
298 Store##Type##NoWriteBarrier##Operator kStore##Type##NoWriteBarrier; \ | 304 Store##Type##NoWriteBarrier##Operator kStore##Type##NoWriteBarrier; \ |
299 Store##Type##MapWriteBarrier##Operator kStore##Type##MapWriteBarrier; \ | 305 Store##Type##MapWriteBarrier##Operator kStore##Type##MapWriteBarrier; \ |
300 Store##Type##PointerWriteBarrier##Operator \ | 306 Store##Type##PointerWriteBarrier##Operator \ |
301 kStore##Type##PointerWriteBarrier; \ | 307 kStore##Type##PointerWriteBarrier; \ |
302 Store##Type##FullWriteBarrier##Operator kStore##Type##FullWriteBarrier; \ | 308 Store##Type##FullWriteBarrier##Operator kStore##Type##FullWriteBarrier; \ |
303 CheckedStore##Type##Operator kCheckedStore##Type; | 309 CheckedStore##Type##Operator kCheckedStore##Type; |
304 MACHINE_TYPE_LIST(STORE) | 310 MACHINE_TYPE_LIST(STORE) |
305 #undef STORE | 311 #undef STORE |
306 }; | 312 }; |
307 | 313 |
308 | 314 |
309 static base::LazyInstance<MachineOperatorGlobalCache>::type kCache = | 315 static base::LazyInstance<MachineOperatorGlobalCache>::type kCache = |
310 LAZY_INSTANCE_INITIALIZER; | 316 LAZY_INSTANCE_INITIALIZER; |
311 | 317 |
312 | 318 |
313 MachineOperatorBuilder::MachineOperatorBuilder(Zone* zone, MachineType word, | 319 MachineOperatorBuilder::MachineOperatorBuilder(Zone* zone, |
| 320 MachineRepresentation word, |
314 Flags flags) | 321 Flags flags) |
315 : cache_(kCache.Get()), word_(word), flags_(flags) { | 322 : cache_(kCache.Get()), word_(word), flags_(flags) { |
316 DCHECK(word == kRepWord32 || word == kRepWord64); | 323 DCHECK(word == MachineRepresentation::kWord32 || |
| 324 word == MachineRepresentation::kWord64); |
317 } | 325 } |
318 | 326 |
319 | 327 |
320 #define PURE(Name, properties, value_input_count, control_input_count, \ | 328 #define PURE(Name, properties, value_input_count, control_input_count, \ |
321 output_count) \ | 329 output_count) \ |
322 const Operator* MachineOperatorBuilder::Name() { return &cache_.k##Name; } | 330 const Operator* MachineOperatorBuilder::Name() { return &cache_.k##Name; } |
323 PURE_OP_LIST(PURE) | 331 PURE_OP_LIST(PURE) |
324 #undef PURE | 332 #undef PURE |
325 | 333 |
326 #define PURE(Name, properties, value_input_count, control_input_count, \ | 334 #define PURE(Name, properties, value_input_count, control_input_count, \ |
(...skipping 12 matching lines...) Expand all Loading... |
339 return &cache_.kTruncateFloat64ToInt32JavaScript; | 347 return &cache_.kTruncateFloat64ToInt32JavaScript; |
340 case TruncationMode::kRoundToZero: | 348 case TruncationMode::kRoundToZero: |
341 return &cache_.kTruncateFloat64ToInt32RoundToZero; | 349 return &cache_.kTruncateFloat64ToInt32RoundToZero; |
342 } | 350 } |
343 UNREACHABLE(); | 351 UNREACHABLE(); |
344 return nullptr; | 352 return nullptr; |
345 } | 353 } |
346 | 354 |
347 | 355 |
348 const Operator* MachineOperatorBuilder::Load(LoadRepresentation rep) { | 356 const Operator* MachineOperatorBuilder::Load(LoadRepresentation rep) { |
349 switch (rep) { | 357 #define LOAD(Type) \ |
350 #define LOAD(Type) \ | 358 if (rep == MachineType::Type()) { \ |
351 case k##Type: \ | 359 return &cache_.kLoad##Type; \ |
352 return &cache_.kLoad##Type; | 360 } |
353 MACHINE_TYPE_LIST(LOAD) | 361 MACHINE_TYPE_LIST(LOAD) |
354 #undef LOAD | 362 #undef LOAD |
355 default: | |
356 break; | |
357 } | |
358 UNREACHABLE(); | 363 UNREACHABLE(); |
359 return nullptr; | 364 return nullptr; |
360 } | 365 } |
361 | 366 |
362 | 367 |
363 const Operator* MachineOperatorBuilder::Store(StoreRepresentation rep) { | 368 const Operator* MachineOperatorBuilder::Store(StoreRepresentation store_rep) { |
364 switch (rep.machine_type()) { | 369 MachineType type = store_rep.machine_type(); |
365 #define STORE(Type) \ | 370 #define STORE(Type) \ |
366 case k##Type: \ | 371 if (type == MachineType::Type()) { \ |
367 switch (rep.write_barrier_kind()) { \ | 372 switch (store_rep.write_barrier_kind()) { \ |
368 case kNoWriteBarrier: \ | 373 case kNoWriteBarrier: \ |
369 return &cache_.k##Store##Type##NoWriteBarrier; \ | 374 return &cache_.k##Store##Type##NoWriteBarrier; \ |
370 case kMapWriteBarrier: \ | 375 case kMapWriteBarrier: \ |
371 return &cache_.k##Store##Type##MapWriteBarrier; \ | 376 return &cache_.k##Store##Type##MapWriteBarrier; \ |
372 case kPointerWriteBarrier: \ | 377 case kPointerWriteBarrier: \ |
373 return &cache_.k##Store##Type##PointerWriteBarrier; \ | 378 return &cache_.k##Store##Type##PointerWriteBarrier; \ |
374 case kFullWriteBarrier: \ | 379 case kFullWriteBarrier: \ |
375 return &cache_.k##Store##Type##FullWriteBarrier; \ | 380 return &cache_.k##Store##Type##FullWriteBarrier; \ |
376 } \ | 381 } \ |
377 break; | 382 } |
378 MACHINE_TYPE_LIST(STORE) | 383 MACHINE_TYPE_LIST(STORE) |
379 #undef STORE | 384 #undef STORE |
380 | |
381 default: | |
382 break; | |
383 } | |
384 UNREACHABLE(); | 385 UNREACHABLE(); |
385 return nullptr; | 386 return nullptr; |
386 } | 387 } |
387 | 388 |
388 | 389 |
389 const Operator* MachineOperatorBuilder::CheckedLoad( | 390 const Operator* MachineOperatorBuilder::CheckedLoad( |
390 CheckedLoadRepresentation rep) { | 391 CheckedLoadRepresentation rep) { |
391 switch (rep) { | 392 #define LOAD(Type) \ |
392 #define LOAD(Type) \ | 393 if (rep == MachineType::Type()) { \ |
393 case k##Type: \ | 394 return &cache_.kCheckedLoad##Type; \ |
394 return &cache_.kCheckedLoad##Type; | 395 } |
395 MACHINE_TYPE_LIST(LOAD) | 396 MACHINE_TYPE_LIST(LOAD) |
396 #undef LOAD | 397 #undef LOAD |
397 default: | |
398 break; | |
399 } | |
400 UNREACHABLE(); | 398 UNREACHABLE(); |
401 return nullptr; | 399 return nullptr; |
402 } | 400 } |
403 | 401 |
404 | 402 |
405 const Operator* MachineOperatorBuilder::CheckedStore( | 403 const Operator* MachineOperatorBuilder::CheckedStore( |
406 CheckedStoreRepresentation rep) { | 404 CheckedStoreRepresentation rep) { |
407 switch (rep) { | 405 #define STORE(Type) \ |
408 #define STORE(Type) \ | 406 if (rep == MachineType::Type()) { \ |
409 case k##Type: \ | 407 return &cache_.kCheckedStore##Type; \ |
410 return &cache_.kCheckedStore##Type; | 408 } |
411 MACHINE_TYPE_LIST(STORE) | 409 MACHINE_TYPE_LIST(STORE) |
412 #undef STORE | 410 #undef STORE |
413 default: | |
414 break; | |
415 } | |
416 UNREACHABLE(); | 411 UNREACHABLE(); |
417 return nullptr; | 412 return nullptr; |
418 } | 413 } |
419 | 414 |
420 } // namespace compiler | 415 } // namespace compiler |
421 } // namespace internal | 416 } // namespace internal |
422 } // namespace v8 | 417 } // namespace v8 |
OLD | NEW |