Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(56)

Side by Side Diff: src/compiler/ast-graph-builder.cc

Issue 2035383003: [turbofan] Type feedback for numeric comparisons. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Rebase, pure ops Created 4 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | src/compiler/bytecode-graph-builder.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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/ast-graph-builder.h" 5 #include "src/compiler/ast-graph-builder.h"
6 6
7 #include "src/ast/scopes.h" 7 #include "src/ast/scopes.h"
8 #include "src/compiler.h" 8 #include "src/compiler.h"
9 #include "src/compiler/ast-loop-assignment-analyzer.h" 9 #include "src/compiler/ast-loop-assignment-analyzer.h"
10 #include "src/compiler/control-builders.h" 10 #include "src/compiler/control-builders.h"
(...skipping 263 matching lines...) Expand 10 before | Expand all | Expand 10 after
274 } 274 }
275 275
276 protected: 276 protected:
277 Node* NewPathToken(int token_id) { 277 Node* NewPathToken(int token_id) {
278 return owner_->jsgraph()->Constant(token_id); 278 return owner_->jsgraph()->Constant(token_id);
279 } 279 }
280 Node* NewPathTokenForImplicitFallThrough() { 280 Node* NewPathTokenForImplicitFallThrough() {
281 return NewPathToken(TokenDispenserForFinally::kFallThroughToken); 281 return NewPathToken(TokenDispenserForFinally::kFallThroughToken);
282 } 282 }
283 Node* NewPathDispatchCondition(Node* t1, Node* t2) { 283 Node* NewPathDispatchCondition(Node* t1, Node* t2) {
284 return owner_->NewNode(owner_->javascript()->StrictEqual(), t1, t2); 284 return owner_->NewNode(
285 owner_->javascript()->StrictEqual(CompareOperationHints::Any()), t1,
286 t2);
285 } 287 }
286 288
287 private: 289 private:
288 TokenDispenserForFinally dispenser_; 290 TokenDispenserForFinally dispenser_;
289 AstGraphBuilder* owner_; 291 AstGraphBuilder* owner_;
290 ZoneVector<Entry> deferred_; 292 ZoneVector<Entry> deferred_;
291 Node* return_token_; 293 Node* return_token_;
292 Node* throw_token_; 294 Node* throw_token_;
293 }; 295 };
294 296
(...skipping 1001 matching lines...) Expand 10 before | Expand all | Expand 10 after
1296 if (clause->is_default()) { 1298 if (clause->is_default()) {
1297 default_index = i; 1299 default_index = i;
1298 continue; 1300 continue;
1299 } 1301 }
1300 1302
1301 // Create nodes to perform label comparison as if via '==='. The switch 1303 // Create nodes to perform label comparison as if via '==='. The switch
1302 // value is still on the operand stack while the label is evaluated. 1304 // value is still on the operand stack while the label is evaluated.
1303 VisitForValue(clause->label()); 1305 VisitForValue(clause->label());
1304 Node* label = environment()->Pop(); 1306 Node* label = environment()->Pop();
1305 Node* tag = environment()->Top(); 1307 Node* tag = environment()->Top();
1306 const Operator* op = javascript()->StrictEqual(); 1308
1309 CompareOperationHints hints;
1310 if (!type_hint_analysis_ ||
1311 !type_hint_analysis_->GetCompareOperationHints(clause->CompareId(),
1312 &hints)) {
1313 hints = CompareOperationHints::Any();
1314 }
1315
1316 const Operator* op = javascript()->StrictEqual(hints);
1307 Node* condition = NewNode(op, tag, label); 1317 Node* condition = NewNode(op, tag, label);
1308 compare_switch.BeginLabel(i, condition); 1318 compare_switch.BeginLabel(i, condition);
1309 1319
1310 // Discard the switch value at label match. 1320 // Discard the switch value at label match.
1311 environment()->Pop(); 1321 environment()->Pop();
1312 compare_switch.EndLabel(); 1322 compare_switch.EndLabel();
1313 } 1323 }
1314 1324
1315 // Discard the switch value and mark the default case. 1325 // Discard the switch value and mark the default case.
1316 environment()->Pop(); 1326 environment()->Pop();
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after
1372 } 1382 }
1373 1383
1374 1384
1375 void AstGraphBuilder::VisitForInStatement(ForInStatement* stmt) { 1385 void AstGraphBuilder::VisitForInStatement(ForInStatement* stmt) {
1376 VisitForValue(stmt->subject()); 1386 VisitForValue(stmt->subject());
1377 Node* object = environment()->Pop(); 1387 Node* object = environment()->Pop();
1378 BlockBuilder for_block(this); 1388 BlockBuilder for_block(this);
1379 for_block.BeginBlock(); 1389 for_block.BeginBlock();
1380 // Check for null or undefined before entering loop. 1390 // Check for null or undefined before entering loop.
1381 Node* is_null_cond = 1391 Node* is_null_cond =
1382 NewNode(javascript()->StrictEqual(), object, jsgraph()->NullConstant()); 1392 NewNode(javascript()->StrictEqual(CompareOperationHints::Any()), object,
1393 jsgraph()->NullConstant());
1383 for_block.BreakWhen(is_null_cond, BranchHint::kFalse); 1394 for_block.BreakWhen(is_null_cond, BranchHint::kFalse);
1384 Node* is_undefined_cond = NewNode(javascript()->StrictEqual(), object, 1395 Node* is_undefined_cond =
1385 jsgraph()->UndefinedConstant()); 1396 NewNode(javascript()->StrictEqual(CompareOperationHints::Any()), object,
1397 jsgraph()->UndefinedConstant());
1386 for_block.BreakWhen(is_undefined_cond, BranchHint::kFalse); 1398 for_block.BreakWhen(is_undefined_cond, BranchHint::kFalse);
1387 { 1399 {
1388 // Convert object to jsobject. 1400 // Convert object to jsobject.
1389 object = BuildToObject(object, stmt->ToObjectId()); 1401 object = BuildToObject(object, stmt->ToObjectId());
1390 environment()->Push(object); 1402 environment()->Push(object);
1391 1403
1392 // Prepare for-in cache. 1404 // Prepare for-in cache.
1393 Node* prepare = NewNode(javascript()->ForInPrepare(), object); 1405 Node* prepare = NewNode(javascript()->ForInPrepare(), object);
1394 PrepareFrameState(prepare, stmt->PrepareId(), 1406 PrepareFrameState(prepare, stmt->PrepareId(),
1395 OutputFrameStateCombine::Push(3)); 1407 OutputFrameStateCombine::Push(3));
(...skipping 22 matching lines...) Expand all
1418 // Check loop termination condition. 1430 // Check loop termination condition.
1419 Node* exit_cond = NewNode(javascript()->ForInDone(), index, cache_length); 1431 Node* exit_cond = NewNode(javascript()->ForInDone(), index, cache_length);
1420 for_loop.BreakWhen(exit_cond); 1432 for_loop.BreakWhen(exit_cond);
1421 1433
1422 // Compute the next enumerated value. 1434 // Compute the next enumerated value.
1423 Node* value = NewNode(javascript()->ForInNext(), object, cache_array, 1435 Node* value = NewNode(javascript()->ForInNext(), object, cache_array,
1424 cache_type, index); 1436 cache_type, index);
1425 PrepareFrameState(value, stmt->FilterId(), 1437 PrepareFrameState(value, stmt->FilterId(),
1426 OutputFrameStateCombine::Push()); 1438 OutputFrameStateCombine::Push());
1427 IfBuilder test_value(this); 1439 IfBuilder test_value(this);
1428 Node* test_value_cond = NewNode(javascript()->StrictEqual(), value, 1440 Node* test_value_cond =
1429 jsgraph()->UndefinedConstant()); 1441 NewNode(javascript()->StrictEqual(CompareOperationHints::Any()),
1442 value, jsgraph()->UndefinedConstant());
1430 test_value.If(test_value_cond, BranchHint::kFalse); 1443 test_value.If(test_value_cond, BranchHint::kFalse);
1431 test_value.Then(); 1444 test_value.Then();
1432 test_value.Else(); 1445 test_value.Else();
1433 { 1446 {
1434 // Bind value and do loop body. 1447 // Bind value and do loop body.
1435 VectorSlotPair feedback = 1448 VectorSlotPair feedback =
1436 CreateVectorSlotPair(stmt->EachFeedbackSlot()); 1449 CreateVectorSlotPair(stmt->EachFeedbackSlot());
1437 VisitForInAssignment(stmt->each(), value, feedback, stmt->FilterId(), 1450 VisitForInAssignment(stmt->each(), value, feedback, stmt->FilterId(),
1438 stmt->AssignmentId()); 1451 stmt->AssignmentId());
1439 VisitIterationBody(stmt, &for_loop); 1452 VisitIterationBody(stmt, &for_loop);
(...skipping 1384 matching lines...) Expand 10 before | Expand all | Expand 10 after
2824 } 2837 }
2825 } 2838 }
2826 } 2839 }
2827 2840
2828 void AstGraphBuilder::VisitLiteralCompareNil(CompareOperation* expr, 2841 void AstGraphBuilder::VisitLiteralCompareNil(CompareOperation* expr,
2829 Expression* sub_expr, 2842 Expression* sub_expr,
2830 Node* nil_value) { 2843 Node* nil_value) {
2831 const Operator* op = nullptr; 2844 const Operator* op = nullptr;
2832 switch (expr->op()) { 2845 switch (expr->op()) {
2833 case Token::EQ: 2846 case Token::EQ:
2834 op = javascript()->Equal(); 2847 op = javascript()->Equal(CompareOperationHints::Any());
2835 break; 2848 break;
2836 case Token::EQ_STRICT: 2849 case Token::EQ_STRICT:
2837 op = javascript()->StrictEqual(); 2850 op = javascript()->StrictEqual(CompareOperationHints::Any());
2838 break; 2851 break;
2839 default: 2852 default:
2840 UNREACHABLE(); 2853 UNREACHABLE();
2841 } 2854 }
2842 VisitForValue(sub_expr); 2855 VisitForValue(sub_expr);
2843 PrepareEagerCheckpoint(sub_expr->id()); 2856 PrepareEagerCheckpoint(sub_expr->id());
2844 Node* value_to_compare = environment()->Pop(); 2857 Node* value_to_compare = environment()->Pop();
2845 Node* value = NewNode(op, value_to_compare, nil_value); 2858 Node* value = NewNode(op, value_to_compare, nil_value);
2846 PrepareFrameState(value, expr->id(), ast_context()->GetStateCombine()); 2859 PrepareFrameState(value, expr->id(), ast_context()->GetStateCombine());
2847 return ast_context()->ProduceValue(value); 2860 return ast_context()->ProduceValue(value);
2848 } 2861 }
2849 2862
2850 void AstGraphBuilder::VisitLiteralCompareTypeof(CompareOperation* expr, 2863 void AstGraphBuilder::VisitLiteralCompareTypeof(CompareOperation* expr,
2851 Expression* sub_expr, 2864 Expression* sub_expr,
2852 Handle<String> check) { 2865 Handle<String> check) {
2853 VisitTypeofExpression(sub_expr); 2866 VisitTypeofExpression(sub_expr);
2854 PrepareEagerCheckpoint(sub_expr->id()); 2867 PrepareEagerCheckpoint(sub_expr->id());
2855 Node* typeof_arg = NewNode(javascript()->TypeOf(), environment()->Pop()); 2868 Node* typeof_arg = NewNode(javascript()->TypeOf(), environment()->Pop());
2856 Node* value = NewNode(javascript()->StrictEqual(), typeof_arg, 2869 Node* value = NewNode(javascript()->StrictEqual(CompareOperationHints::Any()),
2857 jsgraph()->Constant(check)); 2870 typeof_arg, jsgraph()->Constant(check));
2858 PrepareFrameState(value, expr->id(), ast_context()->GetStateCombine()); 2871 PrepareFrameState(value, expr->id(), ast_context()->GetStateCombine());
2859 return ast_context()->ProduceValue(value); 2872 return ast_context()->ProduceValue(value);
2860 } 2873 }
2861 2874
2862 void AstGraphBuilder::VisitCompareOperation(CompareOperation* expr) { 2875 void AstGraphBuilder::VisitCompareOperation(CompareOperation* expr) {
2863 // Check for a few fast cases. The AST visiting behavior must be in sync 2876 // Check for a few fast cases. The AST visiting behavior must be in sync
2864 // with the full codegen: We don't push both left and right values onto 2877 // with the full codegen: We don't push both left and right values onto
2865 // the expression stack when one side is a special-case literal. 2878 // the expression stack when one side is a special-case literal.
2866 Expression* sub_expr = nullptr; 2879 Expression* sub_expr = nullptr;
2867 Handle<String> check; 2880 Handle<String> check;
2868 if (expr->IsLiteralCompareTypeof(&sub_expr, &check)) { 2881 if (expr->IsLiteralCompareTypeof(&sub_expr, &check)) {
2869 return VisitLiteralCompareTypeof(expr, sub_expr, check); 2882 return VisitLiteralCompareTypeof(expr, sub_expr, check);
2870 } 2883 }
2871 if (expr->IsLiteralCompareUndefined(&sub_expr)) { 2884 if (expr->IsLiteralCompareUndefined(&sub_expr)) {
2872 return VisitLiteralCompareNil(expr, sub_expr, 2885 return VisitLiteralCompareNil(expr, sub_expr,
2873 jsgraph()->UndefinedConstant()); 2886 jsgraph()->UndefinedConstant());
2874 } 2887 }
2875 if (expr->IsLiteralCompareNull(&sub_expr)) { 2888 if (expr->IsLiteralCompareNull(&sub_expr)) {
2876 return VisitLiteralCompareNil(expr, sub_expr, jsgraph()->NullConstant()); 2889 return VisitLiteralCompareNil(expr, sub_expr, jsgraph()->NullConstant());
2877 } 2890 }
2878 2891
2892 CompareOperationHints hints;
2893 if (!type_hint_analysis_ ||
2894 !type_hint_analysis_->GetCompareOperationHints(
2895 expr->CompareOperationFeedbackId(), &hints)) {
2896 hints = CompareOperationHints::Any();
2897 }
2898
2879 const Operator* op; 2899 const Operator* op;
2880 switch (expr->op()) { 2900 switch (expr->op()) {
2881 case Token::EQ: 2901 case Token::EQ:
2882 op = javascript()->Equal(); 2902 op = javascript()->Equal(hints);
2883 break; 2903 break;
2884 case Token::NE: 2904 case Token::NE:
2885 op = javascript()->NotEqual(); 2905 op = javascript()->NotEqual(hints);
2886 break; 2906 break;
2887 case Token::EQ_STRICT: 2907 case Token::EQ_STRICT:
2888 op = javascript()->StrictEqual(); 2908 op = javascript()->StrictEqual(hints);
2889 break; 2909 break;
2890 case Token::NE_STRICT: 2910 case Token::NE_STRICT:
2891 op = javascript()->StrictNotEqual(); 2911 op = javascript()->StrictNotEqual(hints);
2892 break; 2912 break;
2893 case Token::LT: 2913 case Token::LT:
2894 op = javascript()->LessThan(); 2914 op = javascript()->LessThan(hints);
2895 break; 2915 break;
2896 case Token::GT: 2916 case Token::GT:
2897 op = javascript()->GreaterThan(); 2917 op = javascript()->GreaterThan(hints);
2898 break; 2918 break;
2899 case Token::LTE: 2919 case Token::LTE:
2900 op = javascript()->LessThanOrEqual(); 2920 op = javascript()->LessThanOrEqual(hints);
2901 break; 2921 break;
2902 case Token::GTE: 2922 case Token::GTE:
2903 op = javascript()->GreaterThanOrEqual(); 2923 op = javascript()->GreaterThanOrEqual(hints);
2904 break; 2924 break;
2905 case Token::INSTANCEOF: 2925 case Token::INSTANCEOF:
2906 op = javascript()->InstanceOf(); 2926 op = javascript()->InstanceOf();
2907 break; 2927 break;
2908 case Token::IN: 2928 case Token::IN:
2909 op = javascript()->HasProperty(); 2929 op = javascript()->HasProperty();
2910 break; 2930 break;
2911 default: 2931 default:
2912 op = nullptr; 2932 op = nullptr;
2913 UNREACHABLE(); 2933 UNREACHABLE();
(...skipping 398 matching lines...) Expand 10 before | Expand all | Expand 10 after
3312 BailoutId::None()); 3332 BailoutId::None());
3313 return object; 3333 return object;
3314 } 3334 }
3315 3335
3316 3336
3317 Node* AstGraphBuilder::BuildHoleCheckThenThrow(Node* value, Variable* variable, 3337 Node* AstGraphBuilder::BuildHoleCheckThenThrow(Node* value, Variable* variable,
3318 Node* not_hole, 3338 Node* not_hole,
3319 BailoutId bailout_id) { 3339 BailoutId bailout_id) {
3320 IfBuilder hole_check(this); 3340 IfBuilder hole_check(this);
3321 Node* the_hole = jsgraph()->TheHoleConstant(); 3341 Node* the_hole = jsgraph()->TheHoleConstant();
3322 Node* check = NewNode(javascript()->StrictEqual(), value, the_hole); 3342 Node* check = NewNode(javascript()->StrictEqual(CompareOperationHints::Any()),
3343 value, the_hole);
3323 hole_check.If(check); 3344 hole_check.If(check);
3324 hole_check.Then(); 3345 hole_check.Then();
3325 Node* error = BuildThrowReferenceError(variable, bailout_id); 3346 Node* error = BuildThrowReferenceError(variable, bailout_id);
3326 environment()->Push(error); 3347 environment()->Push(error);
3327 hole_check.Else(); 3348 hole_check.Else();
3328 environment()->Push(not_hole); 3349 environment()->Push(not_hole);
3329 hole_check.End(); 3350 hole_check.End();
3330 return environment()->Pop(); 3351 return environment()->Pop();
3331 } 3352 }
3332 3353
3333 3354
3334 Node* AstGraphBuilder::BuildHoleCheckElseThrow(Node* value, Variable* variable, 3355 Node* AstGraphBuilder::BuildHoleCheckElseThrow(Node* value, Variable* variable,
3335 Node* for_hole, 3356 Node* for_hole,
3336 BailoutId bailout_id) { 3357 BailoutId bailout_id) {
3337 IfBuilder hole_check(this); 3358 IfBuilder hole_check(this);
3338 Node* the_hole = jsgraph()->TheHoleConstant(); 3359 Node* the_hole = jsgraph()->TheHoleConstant();
3339 Node* check = NewNode(javascript()->StrictEqual(), value, the_hole); 3360 Node* check = NewNode(javascript()->StrictEqual(CompareOperationHints::Any()),
3361 value, the_hole);
3340 hole_check.If(check); 3362 hole_check.If(check);
3341 hole_check.Then(); 3363 hole_check.Then();
3342 environment()->Push(for_hole); 3364 environment()->Push(for_hole);
3343 hole_check.Else(); 3365 hole_check.Else();
3344 Node* error = BuildThrowReferenceError(variable, bailout_id); 3366 Node* error = BuildThrowReferenceError(variable, bailout_id);
3345 environment()->Push(error); 3367 environment()->Push(error);
3346 hole_check.End(); 3368 hole_check.End();
3347 return environment()->Pop(); 3369 return environment()->Pop();
3348 } 3370 }
3349 3371
3350 3372
3351 Node* AstGraphBuilder::BuildThrowIfStaticPrototype(Node* name, 3373 Node* AstGraphBuilder::BuildThrowIfStaticPrototype(Node* name,
3352 BailoutId bailout_id) { 3374 BailoutId bailout_id) {
3353 IfBuilder prototype_check(this); 3375 IfBuilder prototype_check(this);
3354 Node* prototype_string = 3376 Node* prototype_string =
3355 jsgraph()->Constant(isolate()->factory()->prototype_string()); 3377 jsgraph()->Constant(isolate()->factory()->prototype_string());
3356 Node* check = NewNode(javascript()->StrictEqual(), name, prototype_string); 3378 Node* check = NewNode(javascript()->StrictEqual(CompareOperationHints::Any()),
3379 name, prototype_string);
3357 prototype_check.If(check); 3380 prototype_check.If(check);
3358 prototype_check.Then(); 3381 prototype_check.Then();
3359 Node* error = BuildThrowStaticPrototypeError(bailout_id); 3382 Node* error = BuildThrowStaticPrototypeError(bailout_id);
3360 environment()->Push(error); 3383 environment()->Push(error);
3361 prototype_check.Else(); 3384 prototype_check.Else();
3362 environment()->Push(name); 3385 environment()->Push(name);
3363 prototype_check.End(); 3386 prototype_check.End();
3364 return environment()->Pop(); 3387 return environment()->Pop();
3365 } 3388 }
3366 3389
(...skipping 529 matching lines...) Expand 10 before | Expand all | Expand 10 after
3896 environment()->Pop(); 3919 environment()->Pop();
3897 fast_block.BeginBlock(); 3920 fast_block.BeginBlock();
3898 3921
3899 // Perform checks whether the fast mode applies, by looking for any 3922 // Perform checks whether the fast mode applies, by looking for any
3900 // extension object which might shadow the optimistic declaration. 3923 // extension object which might shadow the optimistic declaration.
3901 for (int depth = 0; bitset != 0; bitset >>= 1, depth++) { 3924 for (int depth = 0; bitset != 0; bitset >>= 1, depth++) {
3902 if ((bitset & 1) == 0) continue; 3925 if ((bitset & 1) == 0) continue;
3903 Node* load = NewNode( 3926 Node* load = NewNode(
3904 javascript()->LoadContext(depth, Context::EXTENSION_INDEX, false), 3927 javascript()->LoadContext(depth, Context::EXTENSION_INDEX, false),
3905 current_context()); 3928 current_context());
3906 Node* check = NewNode(javascript()->StrictEqual(), load, 3929 Node* check =
3907 jsgraph()->TheHoleConstant()); 3930 NewNode(javascript()->StrictEqual(CompareOperationHints::Any()), load,
3931 jsgraph()->TheHoleConstant());
3908 fast_block.BreakUnless(check, BranchHint::kTrue); 3932 fast_block.BreakUnless(check, BranchHint::kTrue);
3909 } 3933 }
3910 3934
3911 // Fast case, because variable is not shadowed. 3935 // Fast case, because variable is not shadowed.
3912 if (Node* constant = TryLoadGlobalConstant(name)) { 3936 if (Node* constant = TryLoadGlobalConstant(name)) {
3913 environment()->Push(constant); 3937 environment()->Push(constant);
3914 } else { 3938 } else {
3915 // Perform global slot load. 3939 // Perform global slot load.
3916 Node* fast = BuildGlobalLoad(name, feedback, typeof_mode); 3940 Node* fast = BuildGlobalLoad(name, feedback, typeof_mode);
3917 PrepareFrameState(fast, bailout_id, combine); 3941 PrepareFrameState(fast, bailout_id, combine);
(...skipping 24 matching lines...) Expand all
3942 environment()->Pop(); 3966 environment()->Pop();
3943 fast_block.BeginBlock(); 3967 fast_block.BeginBlock();
3944 3968
3945 // Perform checks whether the fast mode applies, by looking for any 3969 // Perform checks whether the fast mode applies, by looking for any
3946 // extension object which might shadow the optimistic declaration. 3970 // extension object which might shadow the optimistic declaration.
3947 for (int depth = 0; bitset != 0; bitset >>= 1, depth++) { 3971 for (int depth = 0; bitset != 0; bitset >>= 1, depth++) {
3948 if ((bitset & 1) == 0) continue; 3972 if ((bitset & 1) == 0) continue;
3949 Node* load = NewNode( 3973 Node* load = NewNode(
3950 javascript()->LoadContext(depth, Context::EXTENSION_INDEX, false), 3974 javascript()->LoadContext(depth, Context::EXTENSION_INDEX, false),
3951 current_context()); 3975 current_context());
3952 Node* check = NewNode(javascript()->StrictEqual(), load, 3976 Node* check =
3953 jsgraph()->TheHoleConstant()); 3977 NewNode(javascript()->StrictEqual(CompareOperationHints::Any()), load,
3978 jsgraph()->TheHoleConstant());
3954 fast_block.BreakUnless(check, BranchHint::kTrue); 3979 fast_block.BreakUnless(check, BranchHint::kTrue);
3955 } 3980 }
3956 3981
3957 // Fast case, because variable is not shadowed. Perform context slot load. 3982 // Fast case, because variable is not shadowed. Perform context slot load.
3958 Variable* local = variable->local_if_not_shadowed(); 3983 Variable* local = variable->local_if_not_shadowed();
3959 DCHECK(local->location() == VariableLocation::CONTEXT); // Must be context. 3984 DCHECK(local->location() == VariableLocation::CONTEXT); // Must be context.
3960 Node* fast = 3985 Node* fast =
3961 BuildVariableLoad(local, bailout_id, feedback, combine, typeof_mode); 3986 BuildVariableLoad(local, bailout_id, feedback, combine, typeof_mode);
3962 environment()->Push(fast); 3987 environment()->Push(fast);
3963 slow_block.Break(); 3988 slow_block.Break();
(...skipping 398 matching lines...) Expand 10 before | Expand all | Expand 10 after
4362 // Phi does not exist yet, introduce one. 4387 // Phi does not exist yet, introduce one.
4363 value = NewPhi(inputs, value, control); 4388 value = NewPhi(inputs, value, control);
4364 value->ReplaceInput(inputs - 1, other); 4389 value->ReplaceInput(inputs - 1, other);
4365 } 4390 }
4366 return value; 4391 return value;
4367 } 4392 }
4368 4393
4369 } // namespace compiler 4394 } // namespace compiler
4370 } // namespace internal 4395 } // namespace internal
4371 } // namespace v8 4396 } // namespace v8
OLDNEW
« no previous file with comments | « no previous file | src/compiler/bytecode-graph-builder.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698