Cut-and-paste port from ia32 to x64: Delay load of trivial left operand of binary operation until after right operand loaded.

Review URL: http://codereview.chromium.org/1736023

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@4552 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
This commit is contained in:
whesse@chromium.org 2010-04-30 08:40:31 +00:00
parent 55e32d2f3b
commit e7a3875bb4
3 changed files with 38 additions and 2 deletions

View File

@ -3531,8 +3531,15 @@ void CodeGenerator::VisitBinaryOperation(BinaryOperation* node) {
overwrite_mode = OVERWRITE_RIGHT;
}
Load(node->left());
Load(node->right());
if (node->left()->IsTrivial()) {
Load(node->right());
Result right = frame_->Pop();
frame_->Push(node->left());
frame_->Push(&right);
} else {
Load(node->left());
Load(node->right());
}
GenericBinaryOperation(node->op(), node->type(), overwrite_mode);
}
}

View File

@ -226,6 +226,31 @@ void VirtualFrame::EmitPush(Heap::RootListIndex index, TypeInfo info) {
}
void VirtualFrame::Push(Expression* expr) {
ASSERT(expr->IsTrivial());
Literal* lit = expr->AsLiteral();
if (lit != NULL) {
Push(lit->handle());
return;
}
VariableProxy* proxy = expr->AsVariableProxy();
if (proxy != NULL) {
Slot* slot = proxy->var()->slot();
if (slot->type() == Slot::LOCAL) {
PushLocalAt(slot->index());
return;
}
if (slot->type() == Slot::PARAMETER) {
PushParameterAt(slot->index());
return;
}
}
UNREACHABLE();
}
void VirtualFrame::Drop(int count) {
ASSERT(count >= 0);
ASSERT(height() >= count);

View File

@ -415,6 +415,10 @@ class VirtualFrame : public ZoneObject {
result->Unuse();
}
// Pushing an expression expects that the expression is trivial (according
// to Expression::IsTrivial).
void Push(Expression* expr);
// Nip removes zero or more elements from immediately below the top
// of the frame, leaving the previous top-of-frame value on top of
// the frame. Nip(k) is equivalent to x = Pop(), Drop(k), Push(x).