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/code-factory.h" | 5 #include "src/code-factory.h" |
6 #include "src/compiler/access-builder.h" | 6 #include "src/compiler/access-builder.h" |
7 #include "src/compiler/js-graph.h" | 7 #include "src/compiler/js-graph.h" |
8 #include "src/compiler/js-operator.h" | 8 #include "src/compiler/js-operator.h" |
9 #include "src/compiler/js-typed-lowering.h" | 9 #include "src/compiler/js-typed-lowering.h" |
10 #include "src/compiler/machine-operator.h" | 10 #include "src/compiler/machine-operator.h" |
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
105 }; | 105 }; |
106 | 106 |
107 | 107 |
108 // ----------------------------------------------------------------------------- | 108 // ----------------------------------------------------------------------------- |
109 // JSUnaryNot | 109 // JSUnaryNot |
110 | 110 |
111 | 111 |
112 TEST_F(JSTypedLoweringTest, JSUnaryNotWithBoolean) { | 112 TEST_F(JSTypedLoweringTest, JSUnaryNotWithBoolean) { |
113 Node* input = Parameter(Type::Boolean(), 0); | 113 Node* input = Parameter(Type::Boolean(), 0); |
114 Node* context = Parameter(Type::Any(), 1); | 114 Node* context = Parameter(Type::Any(), 1); |
115 Reduction r = | 115 Reduction r = Reduce(graph()->NewNode(javascript()->UnaryNot(), input, |
116 Reduce(graph()->NewNode(javascript()->UnaryNot(), input, context)); | 116 context, graph()->start())); |
117 ASSERT_TRUE(r.Changed()); | 117 ASSERT_TRUE(r.Changed()); |
118 EXPECT_THAT(r.replacement(), IsBooleanNot(input)); | 118 EXPECT_THAT(r.replacement(), IsBooleanNot(input)); |
119 } | 119 } |
120 | 120 |
121 | 121 |
122 TEST_F(JSTypedLoweringTest, JSUnaryNotWithOrderedNumber) { | 122 TEST_F(JSTypedLoweringTest, JSUnaryNotWithOrderedNumber) { |
123 Node* input = Parameter(Type::OrderedNumber(), 0); | 123 Node* input = Parameter(Type::OrderedNumber(), 0); |
124 Node* context = Parameter(Type::Any(), 1); | 124 Node* context = Parameter(Type::Any(), 1); |
125 Reduction r = | 125 Reduction r = Reduce(graph()->NewNode(javascript()->UnaryNot(), input, |
126 Reduce(graph()->NewNode(javascript()->UnaryNot(), input, context)); | 126 context, graph()->start())); |
127 ASSERT_TRUE(r.Changed()); | 127 ASSERT_TRUE(r.Changed()); |
128 EXPECT_THAT(r.replacement(), IsNumberEqual(input, IsNumberConstant(0))); | 128 EXPECT_THAT(r.replacement(), IsNumberEqual(input, IsNumberConstant(0))); |
129 } | 129 } |
130 | 130 |
131 | 131 |
132 TEST_F(JSTypedLoweringTest, JSUnaryNotWithFalsish) { | 132 TEST_F(JSTypedLoweringTest, JSUnaryNotWithFalsish) { |
133 Node* input = Parameter( | 133 Node* input = Parameter( |
134 Type::Union( | 134 Type::Union( |
135 Type::MinusZero(), | 135 Type::MinusZero(), |
136 Type::Union( | 136 Type::Union( |
137 Type::NaN(), | 137 Type::NaN(), |
138 Type::Union( | 138 Type::Union( |
139 Type::Null(), | 139 Type::Null(), |
140 Type::Union( | 140 Type::Union( |
141 Type::Undefined(), | 141 Type::Undefined(), |
142 Type::Union( | 142 Type::Union( |
143 Type::Undetectable(), | 143 Type::Undetectable(), |
144 Type::Union( | 144 Type::Union( |
145 Type::Constant(factory()->false_value(), zone()), | 145 Type::Constant(factory()->false_value(), zone()), |
146 Type::Range(0.0, 0.0, zone()), zone()), | 146 Type::Range(0.0, 0.0, zone()), zone()), |
147 zone()), | 147 zone()), |
148 zone()), | 148 zone()), |
149 zone()), | 149 zone()), |
150 zone()), | 150 zone()), |
151 zone()), | 151 zone()), |
152 0); | 152 0); |
153 Node* context = Parameter(Type::Any(), 1); | 153 Node* context = Parameter(Type::Any(), 1); |
154 Reduction r = | 154 Reduction r = Reduce(graph()->NewNode(javascript()->UnaryNot(), input, |
155 Reduce(graph()->NewNode(javascript()->UnaryNot(), input, context)); | 155 context, graph()->start())); |
156 ASSERT_TRUE(r.Changed()); | 156 ASSERT_TRUE(r.Changed()); |
157 EXPECT_THAT(r.replacement(), IsTrueConstant()); | 157 EXPECT_THAT(r.replacement(), IsTrueConstant()); |
158 } | 158 } |
159 | 159 |
160 | 160 |
161 TEST_F(JSTypedLoweringTest, JSUnaryNotWithTruish) { | 161 TEST_F(JSTypedLoweringTest, JSUnaryNotWithTruish) { |
162 Node* input = Parameter( | 162 Node* input = Parameter( |
163 Type::Union( | 163 Type::Union( |
164 Type::Constant(factory()->true_value(), zone()), | 164 Type::Constant(factory()->true_value(), zone()), |
165 Type::Union(Type::DetectableReceiver(), Type::Symbol(), zone()), | 165 Type::Union(Type::DetectableReceiver(), Type::Symbol(), zone()), |
166 zone()), | 166 zone()), |
167 0); | 167 0); |
168 Node* context = Parameter(Type::Any(), 1); | 168 Node* context = Parameter(Type::Any(), 1); |
169 Reduction r = | 169 Reduction r = Reduce(graph()->NewNode(javascript()->UnaryNot(), input, |
170 Reduce(graph()->NewNode(javascript()->UnaryNot(), input, context)); | 170 context, graph()->start())); |
171 ASSERT_TRUE(r.Changed()); | 171 ASSERT_TRUE(r.Changed()); |
172 EXPECT_THAT(r.replacement(), IsFalseConstant()); | 172 EXPECT_THAT(r.replacement(), IsFalseConstant()); |
173 } | 173 } |
174 | 174 |
175 | 175 |
176 TEST_F(JSTypedLoweringTest, JSUnaryNotWithNonZeroPlainNumber) { | 176 TEST_F(JSTypedLoweringTest, JSUnaryNotWithNonZeroPlainNumber) { |
177 Node* input = Parameter(Type::Range(1.0, 42.0, zone()), 0); | 177 Node* input = Parameter(Type::Range(1.0, 42.0, zone()), 0); |
178 Node* context = Parameter(Type::Any(), 1); | 178 Node* context = Parameter(Type::Any(), 1); |
179 Reduction r = | 179 Reduction r = Reduce(graph()->NewNode(javascript()->UnaryNot(), input, |
180 Reduce(graph()->NewNode(javascript()->UnaryNot(), input, context)); | 180 context, graph()->start())); |
181 ASSERT_TRUE(r.Changed()); | 181 ASSERT_TRUE(r.Changed()); |
182 EXPECT_THAT(r.replacement(), IsFalseConstant()); | 182 EXPECT_THAT(r.replacement(), IsFalseConstant()); |
183 } | 183 } |
184 | 184 |
185 | 185 |
186 TEST_F(JSTypedLoweringTest, JSUnaryNotWithString) { | 186 TEST_F(JSTypedLoweringTest, JSUnaryNotWithString) { |
187 Node* input = Parameter(Type::String(), 0); | 187 Node* input = Parameter(Type::String(), 0); |
188 Node* context = Parameter(Type::Any(), 1); | 188 Node* context = Parameter(Type::Any(), 1); |
189 Reduction r = | 189 Reduction r = Reduce(graph()->NewNode(javascript()->UnaryNot(), input, |
190 Reduce(graph()->NewNode(javascript()->UnaryNot(), input, context)); | 190 context, graph()->start())); |
191 ASSERT_TRUE(r.Changed()); | 191 ASSERT_TRUE(r.Changed()); |
192 EXPECT_THAT( | 192 EXPECT_THAT( |
193 r.replacement(), | 193 r.replacement(), |
194 IsNumberEqual(IsLoadField(AccessBuilder::ForStringLength(zone()), input, | 194 IsNumberEqual(IsLoadField(AccessBuilder::ForStringLength(zone()), input, |
195 graph()->start(), graph()->start()), | 195 graph()->start(), graph()->start()), |
196 IsNumberConstant(0.0))); | 196 IsNumberConstant(0.0))); |
197 } | 197 } |
198 | 198 |
199 | 199 |
200 TEST_F(JSTypedLoweringTest, JSUnaryNotWithAny) { | 200 TEST_F(JSTypedLoweringTest, JSUnaryNotWithAny) { |
201 Node* input = Parameter(Type::Any(), 0); | 201 Node* input = Parameter(Type::Any(), 0); |
202 Node* context = Parameter(Type::Any(), 1); | 202 Node* context = Parameter(Type::Any(), 1); |
203 Reduction r = | 203 Reduction r = Reduce(graph()->NewNode(javascript()->UnaryNot(), input, |
204 Reduce(graph()->NewNode(javascript()->UnaryNot(), input, context)); | 204 context, graph()->start())); |
205 ASSERT_FALSE(r.Changed()); | 205 ASSERT_FALSE(r.Changed()); |
206 } | 206 } |
207 | 207 |
208 | 208 |
209 // ----------------------------------------------------------------------------- | 209 // ----------------------------------------------------------------------------- |
210 // Constant propagation | 210 // Constant propagation |
211 | 211 |
212 | 212 |
213 TEST_F(JSTypedLoweringTest, ParameterWithMinusZero) { | 213 TEST_F(JSTypedLoweringTest, ParameterWithMinusZero) { |
214 { | 214 { |
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
300 } | 300 } |
301 | 301 |
302 | 302 |
303 // ----------------------------------------------------------------------------- | 303 // ----------------------------------------------------------------------------- |
304 // JSToBoolean | 304 // JSToBoolean |
305 | 305 |
306 | 306 |
307 TEST_F(JSTypedLoweringTest, JSToBooleanWithBoolean) { | 307 TEST_F(JSTypedLoweringTest, JSToBooleanWithBoolean) { |
308 Node* input = Parameter(Type::Boolean(), 0); | 308 Node* input = Parameter(Type::Boolean(), 0); |
309 Node* context = Parameter(Type::Any(), 1); | 309 Node* context = Parameter(Type::Any(), 1); |
310 Reduction r = | 310 Reduction r = Reduce(graph()->NewNode(javascript()->ToBoolean(), input, |
311 Reduce(graph()->NewNode(javascript()->ToBoolean(), input, context)); | 311 context, graph()->start())); |
312 ASSERT_TRUE(r.Changed()); | 312 ASSERT_TRUE(r.Changed()); |
313 EXPECT_EQ(input, r.replacement()); | 313 EXPECT_EQ(input, r.replacement()); |
314 } | 314 } |
315 | 315 |
316 | 316 |
317 TEST_F(JSTypedLoweringTest, JSToBooleanWithFalsish) { | 317 TEST_F(JSTypedLoweringTest, JSToBooleanWithFalsish) { |
318 Node* input = Parameter( | 318 Node* input = Parameter( |
319 Type::Union( | 319 Type::Union( |
320 Type::MinusZero(), | 320 Type::MinusZero(), |
321 Type::Union( | 321 Type::Union( |
322 Type::NaN(), | 322 Type::NaN(), |
323 Type::Union( | 323 Type::Union( |
324 Type::Null(), | 324 Type::Null(), |
325 Type::Union( | 325 Type::Union( |
326 Type::Undefined(), | 326 Type::Undefined(), |
327 Type::Union( | 327 Type::Union( |
328 Type::Undetectable(), | 328 Type::Undetectable(), |
329 Type::Union( | 329 Type::Union( |
330 Type::Constant(factory()->false_value(), zone()), | 330 Type::Constant(factory()->false_value(), zone()), |
331 Type::Range(0.0, 0.0, zone()), zone()), | 331 Type::Range(0.0, 0.0, zone()), zone()), |
332 zone()), | 332 zone()), |
333 zone()), | 333 zone()), |
334 zone()), | 334 zone()), |
335 zone()), | 335 zone()), |
336 zone()), | 336 zone()), |
337 0); | 337 0); |
338 Node* context = Parameter(Type::Any(), 1); | 338 Node* context = Parameter(Type::Any(), 1); |
339 Reduction r = | 339 Reduction r = Reduce(graph()->NewNode(javascript()->ToBoolean(), input, |
340 Reduce(graph()->NewNode(javascript()->ToBoolean(), input, context)); | 340 context, graph()->start())); |
341 ASSERT_TRUE(r.Changed()); | 341 ASSERT_TRUE(r.Changed()); |
342 EXPECT_THAT(r.replacement(), IsFalseConstant()); | 342 EXPECT_THAT(r.replacement(), IsFalseConstant()); |
343 } | 343 } |
344 | 344 |
345 | 345 |
346 TEST_F(JSTypedLoweringTest, JSToBooleanWithTruish) { | 346 TEST_F(JSTypedLoweringTest, JSToBooleanWithTruish) { |
347 Node* input = Parameter( | 347 Node* input = Parameter( |
348 Type::Union( | 348 Type::Union( |
349 Type::Constant(factory()->true_value(), zone()), | 349 Type::Constant(factory()->true_value(), zone()), |
350 Type::Union(Type::DetectableReceiver(), Type::Symbol(), zone()), | 350 Type::Union(Type::DetectableReceiver(), Type::Symbol(), zone()), |
351 zone()), | 351 zone()), |
352 0); | 352 0); |
353 Node* context = Parameter(Type::Any(), 1); | 353 Node* context = Parameter(Type::Any(), 1); |
354 Reduction r = | 354 Reduction r = Reduce(graph()->NewNode(javascript()->ToBoolean(), input, |
355 Reduce(graph()->NewNode(javascript()->ToBoolean(), input, context)); | 355 context, graph()->start())); |
356 ASSERT_TRUE(r.Changed()); | 356 ASSERT_TRUE(r.Changed()); |
357 EXPECT_THAT(r.replacement(), IsTrueConstant()); | 357 EXPECT_THAT(r.replacement(), IsTrueConstant()); |
358 } | 358 } |
359 | 359 |
360 | 360 |
361 TEST_F(JSTypedLoweringTest, JSToBooleanWithNonZeroPlainNumber) { | 361 TEST_F(JSTypedLoweringTest, JSToBooleanWithNonZeroPlainNumber) { |
362 Node* input = Parameter(Type::Range(1, V8_INFINITY, zone()), 0); | 362 Node* input = Parameter(Type::Range(1, V8_INFINITY, zone()), 0); |
363 Node* context = Parameter(Type::Any(), 1); | 363 Node* context = Parameter(Type::Any(), 1); |
364 Reduction r = | 364 Reduction r = Reduce(graph()->NewNode(javascript()->ToBoolean(), input, |
365 Reduce(graph()->NewNode(javascript()->ToBoolean(), input, context)); | 365 context, graph()->start())); |
366 ASSERT_TRUE(r.Changed()); | 366 ASSERT_TRUE(r.Changed()); |
367 EXPECT_THAT(r.replacement(), IsTrueConstant()); | 367 EXPECT_THAT(r.replacement(), IsTrueConstant()); |
368 } | 368 } |
369 | 369 |
370 | 370 |
371 TEST_F(JSTypedLoweringTest, JSToBooleanWithOrderedNumber) { | 371 TEST_F(JSTypedLoweringTest, JSToBooleanWithOrderedNumber) { |
372 Node* input = Parameter(Type::OrderedNumber(), 0); | 372 Node* input = Parameter(Type::OrderedNumber(), 0); |
373 Node* context = Parameter(Type::Any(), 1); | 373 Node* context = Parameter(Type::Any(), 1); |
374 Reduction r = | 374 Reduction r = Reduce(graph()->NewNode(javascript()->ToBoolean(), input, |
375 Reduce(graph()->NewNode(javascript()->ToBoolean(), input, context)); | 375 context, graph()->start())); |
376 ASSERT_TRUE(r.Changed()); | 376 ASSERT_TRUE(r.Changed()); |
377 EXPECT_THAT(r.replacement(), | 377 EXPECT_THAT(r.replacement(), |
378 IsBooleanNot(IsNumberEqual(input, IsNumberConstant(0.0)))); | 378 IsBooleanNot(IsNumberEqual(input, IsNumberConstant(0.0)))); |
379 } | 379 } |
380 | 380 |
381 | 381 |
382 TEST_F(JSTypedLoweringTest, JSToBooleanWithString) { | 382 TEST_F(JSTypedLoweringTest, JSToBooleanWithString) { |
383 Node* input = Parameter(Type::String(), 0); | 383 Node* input = Parameter(Type::String(), 0); |
384 Node* context = Parameter(Type::Any(), 1); | 384 Node* context = Parameter(Type::Any(), 1); |
385 Reduction r = | 385 Reduction r = Reduce(graph()->NewNode(javascript()->ToBoolean(), input, |
386 Reduce(graph()->NewNode(javascript()->ToBoolean(), input, context)); | 386 context, graph()->start())); |
387 ASSERT_TRUE(r.Changed()); | 387 ASSERT_TRUE(r.Changed()); |
388 EXPECT_THAT( | 388 EXPECT_THAT( |
389 r.replacement(), | 389 r.replacement(), |
390 IsNumberLessThan(IsNumberConstant(0.0), | 390 IsNumberLessThan(IsNumberConstant(0.0), |
391 IsLoadField(AccessBuilder::ForStringLength(zone()), | 391 IsLoadField(AccessBuilder::ForStringLength(zone()), |
392 input, graph()->start(), graph()->start()))); | 392 input, graph()->start(), graph()->start()))); |
393 } | 393 } |
394 | 394 |
395 | 395 |
396 TEST_F(JSTypedLoweringTest, JSToBooleanWithAny) { | 396 TEST_F(JSTypedLoweringTest, JSToBooleanWithAny) { |
397 Node* input = Parameter(Type::Any(), 0); | 397 Node* input = Parameter(Type::Any(), 0); |
398 Node* context = Parameter(Type::Any(), 1); | 398 Node* context = Parameter(Type::Any(), 1); |
399 Reduction r = | 399 Reduction r = Reduce(graph()->NewNode(javascript()->ToBoolean(), input, |
400 Reduce(graph()->NewNode(javascript()->ToBoolean(), input, context)); | 400 context, graph()->start())); |
401 ASSERT_FALSE(r.Changed()); | 401 ASSERT_FALSE(r.Changed()); |
402 } | 402 } |
403 | 403 |
404 | 404 |
405 // ----------------------------------------------------------------------------- | 405 // ----------------------------------------------------------------------------- |
406 // JSToNumber | 406 // JSToNumber |
407 | 407 |
408 | 408 |
409 TEST_F(JSTypedLoweringTest, JSToNumberWithPlainPrimitive) { | 409 TEST_F(JSTypedLoweringTest, JSToNumberWithPlainPrimitive) { |
410 Node* const input = Parameter(Type::PlainPrimitive(), 0); | 410 Node* const input = Parameter(Type::PlainPrimitive(), 0); |
(...skipping 11 matching lines...) Expand all Loading... |
422 | 422 |
423 // ----------------------------------------------------------------------------- | 423 // ----------------------------------------------------------------------------- |
424 // JSStrictEqual | 424 // JSStrictEqual |
425 | 425 |
426 | 426 |
427 TEST_F(JSTypedLoweringTest, JSStrictEqualWithTheHole) { | 427 TEST_F(JSTypedLoweringTest, JSStrictEqualWithTheHole) { |
428 Node* const the_hole = HeapConstant(factory()->the_hole_value()); | 428 Node* const the_hole = HeapConstant(factory()->the_hole_value()); |
429 Node* const context = UndefinedConstant(); | 429 Node* const context = UndefinedConstant(); |
430 TRACED_FOREACH(Type*, type, kJSTypes) { | 430 TRACED_FOREACH(Type*, type, kJSTypes) { |
431 Node* const lhs = Parameter(type); | 431 Node* const lhs = Parameter(type); |
432 Reduction r = Reduce( | 432 Reduction r = |
433 graph()->NewNode(javascript()->StrictEqual(), lhs, the_hole, context)); | 433 Reduce(graph()->NewNode(javascript()->StrictEqual(), lhs, the_hole, |
| 434 context, graph()->start(), graph()->start())); |
434 ASSERT_TRUE(r.Changed()); | 435 ASSERT_TRUE(r.Changed()); |
435 EXPECT_THAT(r.replacement(), IsFalseConstant()); | 436 EXPECT_THAT(r.replacement(), IsFalseConstant()); |
436 } | 437 } |
437 } | 438 } |
438 | 439 |
439 | 440 |
440 TEST_F(JSTypedLoweringTest, JSStrictEqualWithUnique) { | 441 TEST_F(JSTypedLoweringTest, JSStrictEqualWithUnique) { |
441 Node* const lhs = Parameter(Type::Unique(), 0); | 442 Node* const lhs = Parameter(Type::Unique(), 0); |
442 Node* const rhs = Parameter(Type::Unique(), 1); | 443 Node* const rhs = Parameter(Type::Unique(), 1); |
443 Node* const context = Parameter(Type::Any(), 2); | 444 Node* const context = Parameter(Type::Any(), 2); |
444 Reduction r = | 445 Reduction r = |
445 Reduce(graph()->NewNode(javascript()->StrictEqual(), lhs, rhs, context)); | 446 Reduce(graph()->NewNode(javascript()->StrictEqual(), lhs, rhs, context, |
| 447 graph()->start(), graph()->start())); |
446 ASSERT_TRUE(r.Changed()); | 448 ASSERT_TRUE(r.Changed()); |
447 EXPECT_THAT(r.replacement(), IsReferenceEqual(Type::Unique(), lhs, rhs)); | 449 EXPECT_THAT(r.replacement(), IsReferenceEqual(Type::Unique(), lhs, rhs)); |
448 } | 450 } |
449 | 451 |
450 | 452 |
451 // ----------------------------------------------------------------------------- | 453 // ----------------------------------------------------------------------------- |
452 // JSShiftLeft | 454 // JSShiftLeft |
453 | 455 |
454 | 456 |
455 TEST_F(JSTypedLoweringTest, JSShiftLeftWithSigned32AndConstant) { | 457 TEST_F(JSTypedLoweringTest, JSShiftLeftWithSigned32AndConstant) { |
(...skipping 647 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1103 EXPECT_THAT(r.replacement(), | 1105 EXPECT_THAT(r.replacement(), |
1104 IsFinish(IsAllocate(IsNumberConstant(Context::SizeFor( | 1106 IsFinish(IsAllocate(IsNumberConstant(Context::SizeFor( |
1105 Context::MIN_CONTEXT_SLOTS)), | 1107 Context::MIN_CONTEXT_SLOTS)), |
1106 effect, control), | 1108 effect, control), |
1107 _)); | 1109 _)); |
1108 } | 1110 } |
1109 | 1111 |
1110 } // namespace compiler | 1112 } // namespace compiler |
1111 } // namespace internal | 1113 } // namespace internal |
1112 } // namespace v8 | 1114 } // namespace v8 |
OLD | NEW |