54ea76dc6b
This optimization does not bring any benefit since all functions have at least a call in the slow-path of the stack-overflow check. I'm suggesting to remove support for this optimization since it does not get triggered currently, therefore is also not tested. Plus we have inlining now, which already makes calls to (small enough) leaf functions fast. Review URL: https://codereview.chromium.org//11086044 git-svn-id: https://dart.googlecode.com/svn/branches/bleeding_edge/dart@13555 260f80e4-7a28-3924-810f-c04153c831b5
80 lines
2.5 KiB
C++
80 lines
2.5 KiB
C++
// Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file
|
|
// for details. All rights reserved. Use of this source code is governed by a
|
|
// BSD-style license that can be found in the LICENSE file.
|
|
|
|
#include "vm/globals.h"
|
|
#if defined(TARGET_ARCH_X64)
|
|
|
|
#include "vm/assembler_macros.h"
|
|
|
|
#include "vm/assembler.h"
|
|
|
|
namespace dart {
|
|
|
|
DECLARE_FLAG(bool, inline_alloc);
|
|
|
|
#define __ assembler->
|
|
|
|
// Static.
|
|
void AssemblerMacros::TryAllocate(Assembler* assembler,
|
|
const Class& cls,
|
|
Label* failure,
|
|
bool near_jump,
|
|
Register instance_reg) {
|
|
ASSERT(failure != NULL);
|
|
if (FLAG_inline_alloc) {
|
|
Heap* heap = Isolate::Current()->heap();
|
|
const intptr_t instance_size = cls.instance_size();
|
|
__ movq(TMP, Immediate(heap->TopAddress()));
|
|
__ movq(instance_reg, Address(TMP, 0));
|
|
__ addq(instance_reg, Immediate(instance_size));
|
|
// instance_reg: potential next object start.
|
|
__ movq(TMP, Immediate(heap->EndAddress()));
|
|
__ cmpq(instance_reg, Address(TMP, 0));
|
|
__ j(ABOVE_EQUAL, failure, near_jump);
|
|
// Successfully allocated the object, now update top to point to
|
|
// next object start and store the class in the class field of object.
|
|
__ movq(TMP, Immediate(heap->TopAddress()));
|
|
__ movq(Address(TMP, 0), instance_reg);
|
|
ASSERT(instance_size >= kHeapObjectTag);
|
|
__ subq(instance_reg, Immediate(instance_size - kHeapObjectTag));
|
|
uword tags = 0;
|
|
tags = RawObject::SizeTag::update(instance_size, tags);
|
|
ASSERT(cls.id() != kIllegalCid);
|
|
tags = RawObject::ClassIdTag::update(cls.id(), tags);
|
|
__ movq(FieldAddress(instance_reg, Object::tags_offset()), Immediate(tags));
|
|
} else {
|
|
__ jmp(failure);
|
|
}
|
|
}
|
|
|
|
|
|
void AssemblerMacros::EnterDartFrame(Assembler* assembler,
|
|
intptr_t frame_size) {
|
|
const intptr_t offset = assembler->CodeSize();
|
|
__ EnterFrame(0);
|
|
Label dart_entry;
|
|
__ call(&dart_entry);
|
|
__ Bind(&dart_entry);
|
|
// Adjust saved PC for any intrinsic code that could have been generated
|
|
// before a frame is created.
|
|
if (offset != 0) {
|
|
__ addq(Address(RSP, 0), Immediate(-offset));
|
|
}
|
|
if (frame_size != 0) {
|
|
__ subq(RSP, Immediate(frame_size));
|
|
}
|
|
}
|
|
|
|
|
|
void AssemblerMacros::EnterStubFrame(Assembler* assembler) {
|
|
__ EnterFrame(0);
|
|
__ pushq(Immediate(0)); // Push 0 in the saved PC area for stub frames.
|
|
}
|
|
|
|
#undef __
|
|
|
|
} // namespace dart
|
|
|
|
#endif // defined TARGET_ARCH_X64
|