Commit b5cbcb35 authored by titzer's avatar titzer Committed by Commit bot

[asm.js] (Re)use temporaries in asm->wasm conversion.

This CL is a prequisite for the stack machine changes, which will need
to use temporaries in various places due to the stack height requirements
on blocks.

R=ahaas@chromium.org,bradnelson@chromium.org
BUG=

Review-Url: https://codereview.chromium.org/2280063002
Cr-Commit-Position: refs/heads/master@{#39001}
parent 88d603bb
...@@ -1099,11 +1099,11 @@ class AsmWasmBuilderImpl final : public AstVisitor<AsmWasmBuilderImpl> { ...@@ -1099,11 +1099,11 @@ class AsmWasmBuilderImpl final : public AstVisitor<AsmWasmBuilderImpl> {
} }
case AsmTyper::kMathAbs: { case AsmTyper::kMathAbs: {
if (call_type == kAstI32) { if (call_type == kAstI32) {
uint32_t tmp = current_function_builder_->AddLocal(kAstI32); WasmTemporary tmp(current_function_builder_, kAstI32);
// if set_local(tmp, x) < 0 // if set_local(tmp, x) < 0
Visit(call->arguments()->at(0)); Visit(call->arguments()->at(0));
current_function_builder_->EmitSetLocal(tmp); current_function_builder_->EmitSetLocal(tmp.index());
byte code[] = {WASM_I8(0)}; byte code[] = {WASM_I8(0)};
current_function_builder_->EmitCode(code, sizeof(code)); current_function_builder_->EmitCode(code, sizeof(code));
current_function_builder_->Emit(kExprI32LtS); current_function_builder_->Emit(kExprI32LtS);
...@@ -1111,12 +1111,12 @@ class AsmWasmBuilderImpl final : public AstVisitor<AsmWasmBuilderImpl> { ...@@ -1111,12 +1111,12 @@ class AsmWasmBuilderImpl final : public AstVisitor<AsmWasmBuilderImpl> {
// then (0 - tmp) // then (0 - tmp)
current_function_builder_->EmitCode(code, sizeof(code)); current_function_builder_->EmitCode(code, sizeof(code));
current_function_builder_->EmitGetLocal(tmp); current_function_builder_->EmitGetLocal(tmp.index());
current_function_builder_->Emit(kExprI32Sub); current_function_builder_->Emit(kExprI32Sub);
// else tmp // else tmp
current_function_builder_->Emit(kExprElse); current_function_builder_->Emit(kExprElse);
current_function_builder_->EmitGetLocal(tmp); current_function_builder_->EmitGetLocal(tmp.index());
// end // end
current_function_builder_->Emit(kExprEnd); current_function_builder_->Emit(kExprEnd);
...@@ -1134,25 +1134,25 @@ class AsmWasmBuilderImpl final : public AstVisitor<AsmWasmBuilderImpl> { ...@@ -1134,25 +1134,25 @@ class AsmWasmBuilderImpl final : public AstVisitor<AsmWasmBuilderImpl> {
case AsmTyper::kMathMin: { case AsmTyper::kMathMin: {
// TODO(bradnelson): Change wasm to match Math.min in asm.js mode. // TODO(bradnelson): Change wasm to match Math.min in asm.js mode.
if (call_type == kAstI32) { if (call_type == kAstI32) {
uint32_t tmp_x = current_function_builder_->AddLocal(kAstI32); WasmTemporary tmp_x(current_function_builder_, kAstI32);
uint32_t tmp_y = current_function_builder_->AddLocal(kAstI32); WasmTemporary tmp_y(current_function_builder_, kAstI32);
// if set_local(tmp_x, x) < set_local(tmp_y, y) // if set_local(tmp_x, x) < set_local(tmp_y, y)
Visit(call->arguments()->at(0)); Visit(call->arguments()->at(0));
current_function_builder_->EmitSetLocal(tmp_x); current_function_builder_->EmitSetLocal(tmp_x.index());
Visit(call->arguments()->at(1)); Visit(call->arguments()->at(1));
current_function_builder_->EmitSetLocal(tmp_y); current_function_builder_->EmitSetLocal(tmp_y.index());
current_function_builder_->Emit(kExprI32LeS); current_function_builder_->Emit(kExprI32LeS);
current_function_builder_->Emit(kExprIf); current_function_builder_->Emit(kExprIf);
// then tmp_x // then tmp_x
current_function_builder_->EmitGetLocal(tmp_x); current_function_builder_->EmitGetLocal(tmp_x.index());
// else tmp_y // else tmp_y
current_function_builder_->Emit(kExprElse); current_function_builder_->Emit(kExprElse);
current_function_builder_->EmitGetLocal(tmp_y); current_function_builder_->EmitGetLocal(tmp_y.index());
current_function_builder_->Emit(kExprEnd); current_function_builder_->Emit(kExprEnd);
} else if (call_type == kAstF32) { } else if (call_type == kAstF32) {
...@@ -1169,26 +1169,26 @@ class AsmWasmBuilderImpl final : public AstVisitor<AsmWasmBuilderImpl> { ...@@ -1169,26 +1169,26 @@ class AsmWasmBuilderImpl final : public AstVisitor<AsmWasmBuilderImpl> {
case AsmTyper::kMathMax: { case AsmTyper::kMathMax: {
// TODO(bradnelson): Change wasm to match Math.max in asm.js mode. // TODO(bradnelson): Change wasm to match Math.max in asm.js mode.
if (call_type == kAstI32) { if (call_type == kAstI32) {
uint32_t tmp_x = current_function_builder_->AddLocal(kAstI32); WasmTemporary tmp_x(current_function_builder_, kAstI32);
uint32_t tmp_y = current_function_builder_->AddLocal(kAstI32); WasmTemporary tmp_y(current_function_builder_, kAstI32);
// if set_local(tmp_x, x) < set_local(tmp_y, y) // if set_local(tmp_x, x) < set_local(tmp_y, y)
Visit(call->arguments()->at(0)); Visit(call->arguments()->at(0));
current_function_builder_->EmitSetLocal(tmp_x); current_function_builder_->EmitSetLocal(tmp_x.index());
Visit(call->arguments()->at(1)); Visit(call->arguments()->at(1));
current_function_builder_->EmitSetLocal(tmp_y); current_function_builder_->EmitSetLocal(tmp_y.index());
current_function_builder_->Emit(kExprI32LeS); current_function_builder_->Emit(kExprI32LeS);
current_function_builder_->Emit(kExprIf); current_function_builder_->Emit(kExprIf);
// then tmp_y // then tmp_y
current_function_builder_->EmitGetLocal(tmp_y); current_function_builder_->EmitGetLocal(tmp_y.index());
// else tmp_x // else tmp_x
current_function_builder_->Emit(kExprElse); current_function_builder_->Emit(kExprElse);
current_function_builder_->EmitGetLocal(tmp_x); current_function_builder_->EmitGetLocal(tmp_x.index());
current_function_builder_->Emit(kExprEnd); current_function_builder_->Emit(kExprEnd);
} else if (call_type == kAstF32) { } else if (call_type == kAstF32) {
......
...@@ -56,7 +56,11 @@ WasmFunctionBuilder::WasmFunctionBuilder(WasmModuleBuilder* builder) ...@@ -56,7 +56,11 @@ WasmFunctionBuilder::WasmFunctionBuilder(WasmModuleBuilder* builder)
signature_index_(0), signature_index_(0),
exported_(0), exported_(0),
body_(builder->zone()), body_(builder->zone()),
name_(builder->zone()) {} name_(builder->zone()),
i32_temps_(builder->zone()),
i64_temps_(builder->zone()),
f32_temps_(builder->zone()),
f64_temps_(builder->zone()) {}
void WasmFunctionBuilder::EmitVarInt(uint32_t val) { void WasmFunctionBuilder::EmitVarInt(uint32_t val) {
byte buffer[8]; byte buffer[8];
......
...@@ -136,12 +136,56 @@ class WasmFunctionBuilder : public ZoneObject { ...@@ -136,12 +136,56 @@ class WasmFunctionBuilder : public ZoneObject {
private: private:
explicit WasmFunctionBuilder(WasmModuleBuilder* builder); explicit WasmFunctionBuilder(WasmModuleBuilder* builder);
friend class WasmModuleBuilder; friend class WasmModuleBuilder;
friend class WasmTemporary;
WasmModuleBuilder* builder_; WasmModuleBuilder* builder_;
LocalDeclEncoder locals_; LocalDeclEncoder locals_;
uint32_t signature_index_; uint32_t signature_index_;
bool exported_; bool exported_;
ZoneVector<uint8_t> body_; ZoneVector<uint8_t> body_;
ZoneVector<char> name_; ZoneVector<char> name_;
ZoneVector<uint32_t> i32_temps_;
ZoneVector<uint32_t> i64_temps_;
ZoneVector<uint32_t> f32_temps_;
ZoneVector<uint32_t> f64_temps_;
};
class WasmTemporary {
public:
WasmTemporary(WasmFunctionBuilder* builder, LocalType type) {
switch (type) {
case kAstI32:
temporary_ = &builder->i32_temps_;
break;
case kAstI64:
temporary_ = &builder->i64_temps_;
break;
case kAstF32:
temporary_ = &builder->f32_temps_;
break;
case kAstF64:
temporary_ = &builder->f64_temps_;
break;
default:
UNREACHABLE();
temporary_ = nullptr;
}
if (temporary_->size() == 0) {
// Allocate a new temporary.
index_ = builder->AddLocal(type);
} else {
// Reuse a previous temporary.
index_ = temporary_->back();
temporary_->pop_back();
}
}
~WasmTemporary() {
temporary_->push_back(index_); // return the temporary to the list.
}
uint32_t index() { return index_; }
private:
ZoneVector<uint32_t>* temporary_;
uint32_t index_;
}; };
// TODO(titzer): kill! // TODO(titzer): kill!
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment