OLD | NEW |
1 // Copyright 2015 the V8 project authors. All rights reserved. | 1 // Copyright 2015 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/v8.h" | 5 #include "src/v8.h" |
6 | 6 |
7 // Required to get M_E etc. in MSVC. | 7 // Required to get M_E etc. in MSVC. |
8 #if defined(_WIN32) | 8 #if defined(_WIN32) |
9 #define _USE_MATH_DEFINES | 9 #define _USE_MATH_DEFINES |
10 #endif | 10 #endif |
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
98 ++i) { | 98 ++i) { |
99 b.AddParam(i->type); | 99 b.AddParam(i->type); |
100 } | 100 } |
101 foreign_init_function_->ExportAs( | 101 foreign_init_function_->ExportAs( |
102 CStrVector(AsmWasmBuilder::foreign_init_name)); | 102 CStrVector(AsmWasmBuilder::foreign_init_name)); |
103 foreign_init_function_->SetSignature(b.Build()); | 103 foreign_init_function_->SetSignature(b.Build()); |
104 for (size_t pos = 0; pos < foreign_variables_.size(); ++pos) { | 104 for (size_t pos = 0; pos < foreign_variables_.size(); ++pos) { |
105 foreign_init_function_->EmitGetLocal(static_cast<uint32_t>(pos)); | 105 foreign_init_function_->EmitGetLocal(static_cast<uint32_t>(pos)); |
106 ForeignVariable* fv = &foreign_variables_[pos]; | 106 ForeignVariable* fv = &foreign_variables_[pos]; |
107 uint32_t index = LookupOrInsertGlobal(fv->var, fv->type); | 107 uint32_t index = LookupOrInsertGlobal(fv->var, fv->type); |
108 foreign_init_function_->EmitWithVarInt(kExprSetGlobal, index); | 108 foreign_init_function_->EmitWithVarUint(kExprSetGlobal, index); |
109 } | 109 } |
110 foreign_init_function_->Emit(kExprEnd); | 110 foreign_init_function_->Emit(kExprEnd); |
111 } | 111 } |
112 | 112 |
113 Handle<FixedArray> GetForeignArgs() { | 113 Handle<FixedArray> GetForeignArgs() { |
114 Handle<FixedArray> ret = isolate_->factory()->NewFixedArray( | 114 Handle<FixedArray> ret = isolate_->factory()->NewFixedArray( |
115 static_cast<int>(foreign_variables_.size())); | 115 static_cast<int>(foreign_variables_.size())); |
116 for (size_t i = 0; i < foreign_variables_.size(); ++i) { | 116 for (size_t i = 0; i < foreign_variables_.size(); ++i) { |
117 ForeignVariable* fv = &foreign_variables_[i]; | 117 ForeignVariable* fv = &foreign_variables_[i]; |
118 ret->set(static_cast<int>(i), *fv->name); | 118 ret->set(static_cast<int>(i), *fv->name); |
(...skipping 192 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
311 RECURSE(Visit(stmt->else_statement())); | 311 RECURSE(Visit(stmt->else_statement())); |
312 } | 312 } |
313 } | 313 } |
314 | 314 |
315 void DoBreakOrContinue(BreakableStatement* target, TargetType type) { | 315 void DoBreakOrContinue(BreakableStatement* target, TargetType type) { |
316 DCHECK_EQ(kFuncScope, scope_); | 316 DCHECK_EQ(kFuncScope, scope_); |
317 for (int i = static_cast<int>(breakable_blocks_.size()) - 1; i >= 0; --i) { | 317 for (int i = static_cast<int>(breakable_blocks_.size()) - 1; i >= 0; --i) { |
318 auto elem = breakable_blocks_.at(i); | 318 auto elem = breakable_blocks_.at(i); |
319 if (elem.first == target && elem.second == type) { | 319 if (elem.first == target && elem.second == type) { |
320 int block_distance = static_cast<int>(breakable_blocks_.size() - i - 1); | 320 int block_distance = static_cast<int>(breakable_blocks_.size() - i - 1); |
321 current_function_builder_->EmitWithVarInt(kExprBr, block_distance); | 321 current_function_builder_->EmitWithVarUint(kExprBr, block_distance); |
322 return; | 322 return; |
323 } | 323 } |
324 } | 324 } |
325 UNREACHABLE(); // statement not found | 325 UNREACHABLE(); // statement not found |
326 } | 326 } |
327 | 327 |
328 void VisitContinueStatement(ContinueStatement* stmt) { | 328 void VisitContinueStatement(ContinueStatement* stmt) { |
329 DoBreakOrContinue(stmt->target(), ContinueTarget); | 329 DoBreakOrContinue(stmt->target(), ContinueTarget); |
330 } | 330 } |
331 | 331 |
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
382 HandleCase(node->right, case_to_block, tag, default_block, if_depth); | 382 HandleCase(node->right, case_to_block, tag, default_block, if_depth); |
383 current_function_builder_->Emit(kExprElse); | 383 current_function_builder_->Emit(kExprElse); |
384 } | 384 } |
385 if (node->begin == node->end) { | 385 if (node->begin == node->end) { |
386 VisitVariableProxy(tag); | 386 VisitVariableProxy(tag); |
387 current_function_builder_->EmitI32Const(node->begin); | 387 current_function_builder_->EmitI32Const(node->begin); |
388 current_function_builder_->Emit(kExprI32Eq); | 388 current_function_builder_->Emit(kExprI32Eq); |
389 current_function_builder_->EmitWithU8(kExprIf, kLocalVoid); | 389 current_function_builder_->EmitWithU8(kExprIf, kLocalVoid); |
390 DCHECK(case_to_block.find(node->begin) != case_to_block.end()); | 390 DCHECK(case_to_block.find(node->begin) != case_to_block.end()); |
391 current_function_builder_->Emit(kExprBr); | 391 current_function_builder_->Emit(kExprBr); |
392 current_function_builder_->EmitVarInt(1 + if_depth + | 392 current_function_builder_->EmitVarUint(1 + if_depth + |
393 case_to_block[node->begin]); | 393 case_to_block[node->begin]); |
394 current_function_builder_->Emit(kExprEnd); | 394 current_function_builder_->Emit(kExprEnd); |
395 } else { | 395 } else { |
396 if (node->begin != 0) { | 396 if (node->begin != 0) { |
397 VisitVariableProxy(tag); | 397 VisitVariableProxy(tag); |
398 current_function_builder_->EmitI32Const(node->begin); | 398 current_function_builder_->EmitI32Const(node->begin); |
399 current_function_builder_->Emit(kExprI32Sub); | 399 current_function_builder_->Emit(kExprI32Sub); |
400 } else { | 400 } else { |
401 VisitVariableProxy(tag); | 401 VisitVariableProxy(tag); |
402 } | 402 } |
403 current_function_builder_->Emit(kExprBrTable); | 403 current_function_builder_->Emit(kExprBrTable); |
404 current_function_builder_->EmitVarInt(node->end - node->begin + 1); | 404 current_function_builder_->EmitVarUint(node->end - node->begin + 1); |
405 for (int v = node->begin; v <= node->end; ++v) { | 405 for (int v = node->begin; v <= node->end; ++v) { |
406 if (case_to_block.find(v) != case_to_block.end()) { | 406 if (case_to_block.find(v) != case_to_block.end()) { |
407 uint32_t target = if_depth + case_to_block[v]; | 407 uint32_t target = if_depth + case_to_block[v]; |
408 current_function_builder_->EmitVarInt(target); | 408 current_function_builder_->EmitVarUint(target); |
409 } else { | 409 } else { |
410 uint32_t target = if_depth + default_block; | 410 uint32_t target = if_depth + default_block; |
411 current_function_builder_->EmitVarInt(target); | 411 current_function_builder_->EmitVarUint(target); |
412 } | 412 } |
413 if (v == kMaxInt) { | 413 if (v == kMaxInt) { |
414 break; | 414 break; |
415 } | 415 } |
416 } | 416 } |
417 uint32_t target = if_depth + default_block; | 417 uint32_t target = if_depth + default_block; |
418 current_function_builder_->EmitVarInt(target); | 418 current_function_builder_->EmitVarUint(target); |
419 } | 419 } |
420 | 420 |
421 while (if_depth-- != prev_if_depth) { | 421 while (if_depth-- != prev_if_depth) { |
422 breakable_blocks_.pop_back(); | 422 breakable_blocks_.pop_back(); |
423 current_function_builder_->Emit(kExprEnd); | 423 current_function_builder_->Emit(kExprEnd); |
424 } | 424 } |
425 } | 425 } |
426 | 426 |
427 void VisitSwitchStatement(SwitchStatement* stmt) { | 427 void VisitSwitchStatement(SwitchStatement* stmt) { |
428 VariableProxy* tag = stmt->tag()->AsVariableProxy(); | 428 VariableProxy* tag = stmt->tag()->AsVariableProxy(); |
(...skipping 27 matching lines...) Expand all Loading... |
456 } | 456 } |
457 } | 457 } |
458 if (!has_default || case_count > 1) { | 458 if (!has_default || case_count > 1) { |
459 int default_block = has_default ? case_count - 1 : case_count; | 459 int default_block = has_default ? case_count - 1 : case_count; |
460 BlockVisitor switch_logic_block(this, nullptr, kExprBlock); | 460 BlockVisitor switch_logic_block(this, nullptr, kExprBlock); |
461 CaseNode* root = OrderCases(&cases, zone_); | 461 CaseNode* root = OrderCases(&cases, zone_); |
462 HandleCase(root, case_to_block, tag, default_block, 0); | 462 HandleCase(root, case_to_block, tag, default_block, 0); |
463 if (root->left != nullptr || root->right != nullptr || | 463 if (root->left != nullptr || root->right != nullptr || |
464 root->begin == root->end) { | 464 root->begin == root->end) { |
465 current_function_builder_->Emit(kExprBr); | 465 current_function_builder_->Emit(kExprBr); |
466 current_function_builder_->EmitVarInt(default_block); | 466 current_function_builder_->EmitVarUint(default_block); |
467 } | 467 } |
468 } | 468 } |
469 for (int i = 0; i < case_count; ++i) { | 469 for (int i = 0; i < case_count; ++i) { |
470 CaseClause* clause = clauses->at(i); | 470 CaseClause* clause = clauses->at(i); |
471 RECURSE(VisitStatements(clause->statements())); | 471 RECURSE(VisitStatements(clause->statements())); |
472 BlockVisitor* v = blocks.at(case_count - i - 1); | 472 BlockVisitor* v = blocks.at(case_count - i - 1); |
473 blocks.pop_back(); | 473 blocks.pop_back(); |
474 delete v; | 474 delete v; |
475 } | 475 } |
476 } | 476 } |
(...skipping 173 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
650 | 650 |
651 void VisitVariableProxy(VariableProxy* expr) { | 651 void VisitVariableProxy(VariableProxy* expr) { |
652 if (scope_ == kFuncScope || scope_ == kInitScope) { | 652 if (scope_ == kFuncScope || scope_ == kInitScope) { |
653 Variable* var = expr->var(); | 653 Variable* var = expr->var(); |
654 if (VisitStdlibConstant(var)) { | 654 if (VisitStdlibConstant(var)) { |
655 return; | 655 return; |
656 } | 656 } |
657 ValueType var_type = TypeOf(expr); | 657 ValueType var_type = TypeOf(expr); |
658 DCHECK_NE(kWasmStmt, var_type); | 658 DCHECK_NE(kWasmStmt, var_type); |
659 if (var->IsContextSlot()) { | 659 if (var->IsContextSlot()) { |
660 current_function_builder_->EmitWithVarInt( | 660 current_function_builder_->EmitWithVarUint( |
661 kExprGetGlobal, LookupOrInsertGlobal(var, var_type)); | 661 kExprGetGlobal, LookupOrInsertGlobal(var, var_type)); |
662 } else { | 662 } else { |
663 current_function_builder_->EmitGetLocal( | 663 current_function_builder_->EmitGetLocal( |
664 LookupOrInsertLocal(var, var_type)); | 664 LookupOrInsertLocal(var, var_type)); |
665 } | 665 } |
666 } else if (scope_ == kExportScope) { | 666 } else if (scope_ == kExportScope) { |
667 Variable* var = expr->var(); | 667 Variable* var = expr->var(); |
668 DCHECK(var->is_function()); | 668 DCHECK(var->is_function()); |
669 WasmFunctionBuilder* function = LookupOrInsertFunction(var); | 669 WasmFunctionBuilder* function = LookupOrInsertFunction(var); |
670 function->ExportAs(CStrVector(AsmWasmBuilder::single_function_name)); | 670 function->ExportAs(CStrVector(AsmWasmBuilder::single_function_name)); |
(...skipping 283 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
954 void EmitAssignment(Assignment* expr, AsmType* type, ValueFate fate) { | 954 void EmitAssignment(Assignment* expr, AsmType* type, ValueFate fate) { |
955 // Match the left hand side of the assignment. | 955 // Match the left hand side of the assignment. |
956 VariableProxy* target_var = expr->target()->AsVariableProxy(); | 956 VariableProxy* target_var = expr->target()->AsVariableProxy(); |
957 if (target_var != nullptr) { | 957 if (target_var != nullptr) { |
958 // Left hand side is a local or a global variable. | 958 // Left hand side is a local or a global variable. |
959 Variable* var = target_var->var(); | 959 Variable* var = target_var->var(); |
960 ValueType var_type = TypeOf(expr); | 960 ValueType var_type = TypeOf(expr); |
961 DCHECK_NE(kWasmStmt, var_type); | 961 DCHECK_NE(kWasmStmt, var_type); |
962 if (var->IsContextSlot()) { | 962 if (var->IsContextSlot()) { |
963 uint32_t index = LookupOrInsertGlobal(var, var_type); | 963 uint32_t index = LookupOrInsertGlobal(var, var_type); |
964 current_function_builder_->EmitWithVarInt(kExprSetGlobal, index); | 964 current_function_builder_->EmitWithVarUint(kExprSetGlobal, index); |
965 if (fate == kLeaveOnStack) { | 965 if (fate == kLeaveOnStack) { |
966 current_function_builder_->EmitWithVarInt(kExprGetGlobal, index); | 966 current_function_builder_->EmitWithVarUint(kExprGetGlobal, index); |
967 } | 967 } |
968 } else { | 968 } else { |
969 if (fate == kDrop) { | 969 if (fate == kDrop) { |
970 current_function_builder_->EmitSetLocal( | 970 current_function_builder_->EmitSetLocal( |
971 LookupOrInsertLocal(var, var_type)); | 971 LookupOrInsertLocal(var, var_type)); |
972 } else { | 972 } else { |
973 current_function_builder_->EmitTeeLocal( | 973 current_function_builder_->EmitTeeLocal( |
974 LookupOrInsertLocal(var, var_type)); | 974 LookupOrInsertLocal(var, var_type)); |
975 } | 975 } |
976 } | 976 } |
(...skipping 489 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1466 vp->var(), sig.Build()); | 1466 vp->var(), sig.Build()); |
1467 VisitCallArgs(expr); | 1467 VisitCallArgs(expr); |
1468 // For non-void functions, we must know the parent node. | 1468 // For non-void functions, we must know the parent node. |
1469 DCHECK_IMPLIES(returns_value, parent_binop != nullptr); | 1469 DCHECK_IMPLIES(returns_value, parent_binop != nullptr); |
1470 DCHECK_IMPLIES(returns_value, parent_binop->left() == expr || | 1470 DCHECK_IMPLIES(returns_value, parent_binop->left() == expr || |
1471 parent_binop->right() == expr); | 1471 parent_binop->right() == expr); |
1472 int pos = expr->position(); | 1472 int pos = expr->position(); |
1473 int parent_pos = returns_value ? parent_binop->position() : pos; | 1473 int parent_pos = returns_value ? parent_binop->position() : pos; |
1474 current_function_builder_->AddAsmWasmOffset(pos, parent_pos); | 1474 current_function_builder_->AddAsmWasmOffset(pos, parent_pos); |
1475 current_function_builder_->Emit(kExprCallFunction); | 1475 current_function_builder_->Emit(kExprCallFunction); |
1476 current_function_builder_->EmitVarInt(index); | 1476 current_function_builder_->EmitVarUint(index); |
1477 } else { | 1477 } else { |
1478 WasmFunctionBuilder* function = LookupOrInsertFunction(vp->var()); | 1478 WasmFunctionBuilder* function = LookupOrInsertFunction(vp->var()); |
1479 VisitCallArgs(expr); | 1479 VisitCallArgs(expr); |
1480 current_function_builder_->AddAsmWasmOffset(expr->position(), | 1480 current_function_builder_->AddAsmWasmOffset(expr->position(), |
1481 expr->position()); | 1481 expr->position()); |
1482 current_function_builder_->Emit(kExprCallFunction); | 1482 current_function_builder_->Emit(kExprCallFunction); |
1483 current_function_builder_->EmitDirectCallIndex( | 1483 current_function_builder_->EmitDirectCallIndex( |
1484 function->func_index()); | 1484 function->func_index()); |
1485 returns_value = function->signature()->return_count() > 0; | 1485 returns_value = function->signature()->return_count() > 0; |
1486 } | 1486 } |
(...skipping 13 matching lines...) Expand all Loading... |
1500 current_function_builder_->Emit(kExprI32Add); | 1500 current_function_builder_->Emit(kExprI32Add); |
1501 WasmTemporary tmp(current_function_builder_, kWasmI32); | 1501 WasmTemporary tmp(current_function_builder_, kWasmI32); |
1502 current_function_builder_->EmitSetLocal(tmp.index()); | 1502 current_function_builder_->EmitSetLocal(tmp.index()); |
1503 | 1503 |
1504 VisitCallArgs(expr); | 1504 VisitCallArgs(expr); |
1505 | 1505 |
1506 current_function_builder_->EmitGetLocal(tmp.index()); | 1506 current_function_builder_->EmitGetLocal(tmp.index()); |
1507 current_function_builder_->AddAsmWasmOffset(expr->position(), | 1507 current_function_builder_->AddAsmWasmOffset(expr->position(), |
1508 expr->position()); | 1508 expr->position()); |
1509 current_function_builder_->Emit(kExprCallIndirect); | 1509 current_function_builder_->Emit(kExprCallIndirect); |
1510 current_function_builder_->EmitVarInt(indices->signature_index); | 1510 current_function_builder_->EmitVarUint(indices->signature_index); |
1511 current_function_builder_->EmitVarInt(0); // table index | 1511 current_function_builder_->EmitVarUint(0); // table index |
1512 returns_value = | 1512 returns_value = |
1513 builder_->GetSignature(indices->signature_index)->return_count() > | 1513 builder_->GetSignature(indices->signature_index)->return_count() > |
1514 0; | 1514 0; |
1515 break; | 1515 break; |
1516 } | 1516 } |
1517 default: | 1517 default: |
1518 UNREACHABLE(); | 1518 UNREACHABLE(); |
1519 } | 1519 } |
1520 return returns_value; | 1520 return returns_value; |
1521 } | 1521 } |
(...skipping 493 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2015 impl.builder_->WriteAsmJsOffsetTable(*asm_offsets_buffer); | 2015 impl.builder_->WriteAsmJsOffsetTable(*asm_offsets_buffer); |
2016 return {module_buffer, asm_offsets_buffer, success}; | 2016 return {module_buffer, asm_offsets_buffer, success}; |
2017 } | 2017 } |
2018 | 2018 |
2019 const char* AsmWasmBuilder::foreign_init_name = "__foreign_init__"; | 2019 const char* AsmWasmBuilder::foreign_init_name = "__foreign_init__"; |
2020 const char* AsmWasmBuilder::single_function_name = "__single_function__"; | 2020 const char* AsmWasmBuilder::single_function_name = "__single_function__"; |
2021 | 2021 |
2022 } // namespace wasm | 2022 } // namespace wasm |
2023 } // namespace internal | 2023 } // namespace internal |
2024 } // namespace v8 | 2024 } // namespace v8 |
OLD | NEW |