Load the native call wrapper via Thread.

R=fschneider@google.com

Review URL: https://codereview.chromium.org//1358773002 .
This commit is contained in:
Ryan Macnak 2015-09-20 13:48:17 -07:00
parent 18faa55764
commit f1a0056430
27 changed files with 44 additions and 195 deletions

View file

@ -265,14 +265,6 @@ intptr_t ObjectPoolWrapper::AddObject(ObjectPool::Entry entry,
}
intptr_t ObjectPoolWrapper::AddExternalLabel(const ExternalLabel* label,
Patchability patchable) {
return AddObject(ObjectPool::Entry(label->address(),
ObjectPool::kExternalLabel),
patchable);
}
intptr_t ObjectPoolWrapper::FindObject(ObjectPool::Entry entry,
Patchability patchable) {
// If the object is not patchable, check if we've already got it in the
@ -300,14 +292,6 @@ intptr_t ObjectPoolWrapper::FindImmediate(uword imm) {
}
intptr_t ObjectPoolWrapper::FindExternalLabel(const ExternalLabel* label,
Patchability patchable) {
return FindObject(ObjectPool::Entry(label->address(),
ObjectPool::kExternalLabel),
patchable);
}
intptr_t ObjectPoolWrapper::FindNativeEntry(const ExternalLabel* label,
Patchability patchable) {
return FindObject(ObjectPool::Entry(label->address(),

View file

@ -290,14 +290,10 @@ class ObjectPoolWrapper : public ValueObject {
intptr_t AddObject(const Object& obj,
Patchability patchable = kNotPatchable);
intptr_t AddImmediate(uword imm);
intptr_t AddExternalLabel(const ExternalLabel* label,
Patchability patchable);
intptr_t FindObject(const Object& obj,
Patchability patchable = kNotPatchable);
intptr_t FindImmediate(uword imm);
intptr_t FindExternalLabel(const ExternalLabel* label,
Patchability patchable);
intptr_t FindNativeEntry(const ExternalLabel* label,
Patchability patchable);

View file

@ -1655,16 +1655,6 @@ void Assembler::LoadUniqueObject(Register rd,
}
void Assembler::LoadExternalLabel(Register rd,
const ExternalLabel* label,
Patchability patchable,
Condition cond) {
const int32_t offset = ObjectPool::element_offset(
object_pool_wrapper_.FindExternalLabel(label, patchable));
LoadWordFromPoolOffset(rd, offset - kHeapObjectTag, PP, cond);
}
void Assembler::LoadFunctionFromCalleePool(Register dst,
const Function& function,
Register new_pp) {

View file

@ -667,10 +667,6 @@ class Assembler : public ValueObject {
void LoadObject(Register rd, const Object& object, Condition cond = AL);
void LoadUniqueObject(Register rd, const Object& object, Condition cond = AL);
void LoadExternalLabel(Register dst,
const ExternalLabel* label,
Patchability patchable,
Condition cond = AL);
void LoadFunctionFromCalleePool(Register dst,
const Function& function,
Register new_pp);

View file

@ -384,18 +384,6 @@ bool Assembler::CanLoadFromObjectPool(const Object& object) const {
}
void Assembler::LoadExternalLabel(Register dst, const ExternalLabel* label) {
if (constant_pool_allowed()) {
const int32_t offset = ObjectPool::element_offset(
object_pool_wrapper_.FindExternalLabel(label, kNotPatchable));
LoadWordFromPoolOffset(dst, offset);
} else {
const int64_t target = static_cast<int64_t>(label->address());
LoadImmediate(dst, target);
}
}
void Assembler::LoadNativeEntry(Register dst,
const ExternalLabel* label) {
const int32_t offset = ObjectPool::element_offset(
@ -404,15 +392,6 @@ void Assembler::LoadNativeEntry(Register dst,
}
void Assembler::LoadExternalLabelFixed(Register dst,
const ExternalLabel* label,
Patchability patchable) {
const int32_t offset = ObjectPool::element_offset(
object_pool_wrapper_.FindExternalLabel(label, patchable));
LoadWordFromPoolOffsetFixed(dst, offset);
}
void Assembler::LoadIsolate(Register dst) {
ldr(dst, Address(THR, Thread::isolate_offset()));
}

View file

@ -1285,11 +1285,7 @@ class Assembler : public ValueObject {
intptr_t FindImmediate(int64_t imm);
bool CanLoadFromObjectPool(const Object& object) const;
void LoadExternalLabel(Register dst, const ExternalLabel* label);
void LoadNativeEntry(Register dst, const ExternalLabel* label);
void LoadExternalLabelFixed(Register dst,
const ExternalLabel* label,
Patchability patchable);
void LoadFunctionFromCalleePool(Register dst,
const Function& function,
Register new_pp);

View file

@ -506,19 +506,6 @@ void Assembler::BranchLink(const ExternalLabel* label) {
}
void Assembler::BranchLink(const ExternalLabel* label, Patchability patchable) {
ASSERT(!in_delay_slot_);
const int32_t offset = ObjectPool::element_offset(
object_pool_wrapper_.FindExternalLabel(label, patchable));
LoadWordFromPoolOffset(CODE_REG, offset - kHeapObjectTag);
lw(T9, FieldAddress(CODE_REG, Code::entry_point_offset()));
jalr(T9);
if (patchable == kPatchable) {
delay_slot_available_ = false; // CodePatcher expects a nop.
}
}
void Assembler::BranchLink(const Code& target, Patchability patchable) {
ASSERT(!in_delay_slot_);
const int32_t offset = ObjectPool::element_offset(
@ -596,15 +583,6 @@ void Assembler::LoadUniqueObject(Register rd, const Object& object) {
}
void Assembler::LoadExternalLabel(Register rd,
const ExternalLabel* label,
Patchability patchable) {
const int32_t offset = ObjectPool::element_offset(
object_pool_wrapper_.FindExternalLabel(label, patchable));
LoadWordFromPoolOffset(rd, offset - kHeapObjectTag);
}
void Assembler::LoadFunctionFromCalleePool(Register dst,
const Function& function,
Register new_pp) {

View file

@ -905,8 +905,6 @@ class Assembler : public ValueObject {
void Branch(const StubEntry& stub_entry, Register pp = PP);
void BranchLink(const ExternalLabel* label, Patchability patchable);
void BranchLink(const StubEntry& stub_entry,
Patchability patchable = kNotPatchable);
@ -1512,9 +1510,6 @@ class Assembler : public ValueObject {
void LoadObject(Register rd, const Object& object);
void LoadUniqueObject(Register rd, const Object& object);
void LoadExternalLabel(Register rd,
const ExternalLabel* label,
Patchability patchable);
void LoadFunctionFromCalleePool(Register dst,
const Function& function,
Register new_pp);

View file

@ -62,15 +62,6 @@ void Assembler::call(Label* label) {
}
void Assembler::LoadExternalLabel(Register dst,
const ExternalLabel* label,
Patchability patchable) {
const int32_t offset = ObjectPool::element_offset(
object_pool_wrapper_.FindExternalLabel(label, patchable));
LoadWordFromPoolOffset(dst, offset - kHeapObjectTag);
}
void Assembler::LoadNativeEntry(Register dst,
const ExternalLabel* label,
Patchability patchable) {

View file

@ -760,9 +760,6 @@ class Assembler : public ValueObject {
void LoadIsolate(Register dst);
void LoadObject(Register dst, const Object& obj);
void LoadUniqueObject(Register dst, const Object& obj);
void LoadExternalLabel(Register dst,
const ExternalLabel* label,
Patchability patchable);
void LoadNativeEntry(Register dst,
const ExternalLabel* label,
Patchability patchable);

View file

@ -946,11 +946,7 @@ void NativeCallInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
const StubEntry* stub_entry;
if (link_lazily()) {
stub_entry = StubCode::CallBootstrapCFunction_entry();
entry = reinterpret_cast<uword>(&NativeEntry::LinkNativeCall);
#if defined(USING_SIMULATOR)
entry = Simulator::RedirectExternalReference(
entry, Simulator::kBootstrapNativeCall, NativeEntry::kNumArguments);
#endif
entry = NativeEntry::LinkNativeCallEntry();
} else {
entry = reinterpret_cast<uword>(native_c_function());
if (is_bootstrap_native() || is_leaf_call) {

View file

@ -800,11 +800,7 @@ void NativeCallInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
const StubEntry* stub_entry;
if (link_lazily()) {
stub_entry = StubCode::CallBootstrapCFunction_entry();
entry = reinterpret_cast<uword>(&NativeEntry::LinkNativeCall);
#if defined(USING_SIMULATOR)
entry = Simulator::RedirectExternalReference(
entry, Simulator::kBootstrapNativeCall, NativeEntry::kNumArguments);
#endif
entry = NativeEntry::LinkNativeCallEntry();
} else {
entry = reinterpret_cast<uword>(native_c_function());
if (is_bootstrap_native() || is_leaf_call) {

View file

@ -833,7 +833,7 @@ void NativeCallInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
const StubEntry* stub_entry;
if (link_lazily()) {
stub_entry = StubCode::CallBootstrapCFunction_entry();
__ movl(ECX, Immediate(NativeEntry::LinkNativeCallLabel().address()));
__ movl(ECX, Immediate(NativeEntry::LinkNativeCallEntry()));
} else {
stub_entry = (is_bootstrap_native() || is_leaf_call) ?
StubCode::CallBootstrapCFunction_entry() :

View file

@ -997,11 +997,7 @@ void NativeCallInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
const StubEntry* stub_entry;
if (link_lazily()) {
stub_entry = StubCode::CallBootstrapCFunction_entry();
entry = reinterpret_cast<uword>(&NativeEntry::LinkNativeCall);
#if defined(USING_SIMULATOR)
entry = Simulator::RedirectExternalReference(
entry, Simulator::kBootstrapNativeCall, NativeEntry::kNumArguments);
#endif
entry = NativeEntry::LinkNativeCallEntry();
} else {
entry = reinterpret_cast<uword>(native_c_function());
if (is_bootstrap_native() || is_leaf_call) {

View file

@ -786,8 +786,8 @@ void NativeCallInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
const StubEntry* stub_entry;
if (link_lazily()) {
stub_entry = StubCode::CallBootstrapCFunction_entry();
__ LoadNativeEntry(
RBX, &NativeEntry::LinkNativeCallLabel(), kPatchable);
ExternalLabel label(NativeEntry::LinkNativeCallEntry());
__ LoadNativeEntry(RBX, &label, kPatchable);
} else {
stub_entry = (is_bootstrap_native() || is_leaf_call)
? StubCode::CallBootstrapCFunction_entry()

View file

@ -23,14 +23,6 @@ DEFINE_FLAG(bool, trace_natives, false,
"Trace invocation of natives (debug mode only)");
static ExternalLabel native_call_label(
reinterpret_cast<uword>(&NativeEntry::NativeCallWrapper));
static ExternalLabel link_native_call_label(
reinterpret_cast<uword>(&NativeEntry::LinkNativeCall));
NativeFunction NativeEntry::ResolveNative(const Library& library,
const String& function_name,
int number_of_arguments,
@ -84,8 +76,13 @@ const uint8_t* NativeEntry::ResolveSymbol(uword pc) {
}
const ExternalLabel& NativeEntry::NativeCallWrapperLabel() {
return native_call_label;
uword NativeEntry::NativeCallWrapperEntry() {
uword entry = reinterpret_cast<uword>(NativeEntry::NativeCallWrapper);
#if defined(USING_SIMULATOR)
entry = Simulator::RedirectExternalReference(
entry, Simulator::kNativeCall, NativeEntry::kNumCallWrapperArguments);
#endif
return entry;
}
@ -167,8 +164,13 @@ static NativeFunction ResolveNativeFunction(Isolate *isolate,
}
const ExternalLabel& NativeEntry::LinkNativeCallLabel() {
return link_native_call_label;
uword NativeEntry::LinkNativeCallEntry() {
uword entry = reinterpret_cast<uword>(NativeEntry::LinkNativeCall);
#if defined(USING_SIMULATOR)
entry = Simulator::RedirectExternalReference(
entry, Simulator::kBootstrapNativeCall, NativeEntry::kNumArguments);
#endif
return entry;
}

View file

@ -114,11 +114,11 @@ class NativeEntry : public AllStatic {
uword pc);
static const uint8_t* ResolveSymbol(uword pc);
static const ExternalLabel& NativeCallWrapperLabel();
static uword NativeCallWrapperEntry();
static void NativeCallWrapper(Dart_NativeArguments args,
Dart_NativeFunction func);
static const ExternalLabel& LinkNativeCallLabel();
static uword LinkNativeCallEntry();
static void LinkNativeCall(Dart_NativeArguments args);
};

View file

@ -11036,7 +11036,6 @@ void ObjectPool::PrintJSONImpl(JSONStream* stream, bool ref) const {
imm = RawValueAt(i);
jsarr.AddValue64(imm);
break;
case ObjectPool::kExternalLabel:
case ObjectPool::kNativeEntry:
imm = RawValueAt(i);
jsarr.AddValueF("0x%" Px, imm);
@ -11049,16 +11048,6 @@ void ObjectPool::PrintJSONImpl(JSONStream* stream, bool ref) const {
}
static const char* DescribeExternalLabel(uword addr) {
const char* stub_name = StubCode::NameOfStub(addr);
if (stub_name != NULL) {
return stub_name;
}
return "UNKNOWN";
}
void ObjectPool::DebugPrint() const {
THR_Print("Object Pool: {\n");
for (intptr_t i = 0; i < Length(); i++) {
@ -11069,10 +11058,6 @@ void ObjectPool::DebugPrint() const {
THR_Print("0x%" Px " %s (obj)\n",
reinterpret_cast<uword>(obj),
Object::Handle(obj).ToCString());
} else if (InfoAt(i) == kExternalLabel) {
uword addr = RawValueAt(i);
THR_Print("0x%" Px " (external label: %s)\n",
addr, DescribeExternalLabel(addr));
} else if (InfoAt(i) == kNativeEntry) {
THR_Print("0x%" Px " (native entry)\n", RawValueAt(i));
} else {

View file

@ -3606,7 +3606,6 @@ class ObjectPool : public Object {
enum EntryType {
kTaggedObject,
kImmediate,
kExternalLabel,
kNativeEntry,
};

View file

@ -1318,20 +1318,10 @@ RawObjectPool* ObjectPool::ReadFrom(SnapshotReader* reader,
result.SetRawValueAt(i, raw_value);
break;
}
case ObjectPool::kExternalLabel: {
// TODO(rmacnak): Relocate.
intptr_t raw_value = reader->Read<intptr_t>();
result.SetRawValueAt(i, raw_value);
break;
}
case ObjectPool::kNativeEntry: {
// Read nothing. Initialize with the lazy link entry.
uword entry = reinterpret_cast<uword>(&NativeEntry::LinkNativeCall);
#if defined(USING_SIMULATOR)
entry = Simulator::RedirectExternalReference(
entry, Simulator::kBootstrapNativeCall, NativeEntry::kNumArguments);
#endif
result.SetRawValueAt(i, entry);
uword new_entry = NativeEntry::LinkNativeCallEntry();
result.SetRawValueAt(i, static_cast<intptr_t>(new_entry));
break;
}
default:
@ -1367,19 +1357,18 @@ void RawObjectPool::WriteTo(SnapshotWriter* writer,
writer->Write<int8_t>(entry_type);
Entry& entry = ptr()->data()[i];
switch (entry_type) {
case ObjectPool::kTaggedObject:
case ObjectPool::kTaggedObject: {
writer->WriteObjectImpl(entry.raw_obj_, kAsReference);
break;
case ObjectPool::kImmediate:
}
case ObjectPool::kImmediate: {
writer->Write<intptr_t>(entry.raw_value_);
break;
case ObjectPool::kExternalLabel:
// TODO(rmacnak): Write symbolically.
writer->Write<intptr_t>(entry.raw_value_);
break;
case ObjectPool::kNativeEntry:
}
case ObjectPool::kNativeEntry: {
// Write nothing. Will initialize with the lazy link entry.
break;
}
default:
UNREACHABLE();
}

View file

@ -192,18 +192,10 @@ void StubCode::GenerateCallNativeCFunctionStub(Assembler* assembler) {
__ mov(R0, Operand(SP)); // Pass the pointer to the NativeArguments.
__ mov(R1, Operand(R5)); // Pass the function entrypoint to call.
// Call native function invocation wrapper or redirection via simulator.
#if defined(USING_SIMULATOR)
uword entry = reinterpret_cast<uword>(NativeEntry::NativeCallWrapper);
const ExternalLabel label(Simulator::RedirectExternalReference(
entry, Simulator::kNativeCall, NativeEntry::kNumCallWrapperArguments));
__ LoadExternalLabel(R2, &label, kNotPatchable);
__ blx(R2);
#else
__ LoadExternalLabel(
LR, &NativeEntry::NativeCallWrapperLabel(), kNotPatchable);
__ ldr(LR, Address(THR, Thread::native_call_wrapper_entry_point_offset()));
__ blx(LR);
#endif
// Mark that the isolate is executing Dart code.
__ LoadImmediate(R2, VMTag::kDartTagId);

View file

@ -214,16 +214,10 @@ void StubCode::GenerateCallNativeCFunctionStub(Assembler* assembler) {
__ mov(CSP, SP);
__ mov(R1, R5); // Pass the function entrypoint to call.
// Call native function invocation wrapper or redirection via simulator.
#if defined(USING_SIMULATOR)
uword entry = reinterpret_cast<uword>(NativeEntry::NativeCallWrapper);
entry = Simulator::RedirectExternalReference(
entry, Simulator::kNativeCall, NativeEntry::kNumCallWrapperArguments);
__ LoadImmediate(R2, entry);
__ blr(R2);
#else
__ BranchLink(&NativeEntry::NativeCallWrapperLabel());
#endif
__ ldr(LR, Address(THR, Thread::native_call_wrapper_entry_point_offset()));
__ blr(LR);
// Restore SP and CSP.
__ mov(SP, CSP);

View file

@ -179,7 +179,8 @@ void StubCode::GenerateCallNativeCFunctionStub(Assembler* assembler) {
__ movl(Address(ESP, 0), EAX); // Pass the pointer to the NativeArguments.
__ movl(Address(ESP, kWordSize), ECX); // Function to call.
__ call(&NativeEntry::NativeCallWrapperLabel());
ExternalLabel label(NativeEntry::NativeCallWrapperEntry());
__ call(&label);
// Mark that the isolate is executing Dart code. EDI is callee saved.
__ movl(Address(EDI, Isolate::vm_tag_offset()),

View file

@ -199,16 +199,10 @@ void StubCode::GenerateCallNativeCFunctionStub(Assembler* assembler) {
__ mov(A1, T5); // Pass the function entrypoint.
__ ReserveAlignedFrameSpace(2 * kWordSize); // Just passing A0, A1.
// Call native wrapper function or redirection via simulator.
#if defined(USING_SIMULATOR)
uword entry = reinterpret_cast<uword>(NativeEntry::NativeCallWrapper);
entry = Simulator::RedirectExternalReference(
entry, Simulator::kNativeCall, NativeEntry::kNumCallWrapperArguments);
__ LoadImmediate(T9, entry);
__ lw(T9, Address(THR, Thread::native_call_wrapper_entry_point_offset()));
__ jalr(T9);
#else
__ BranchLink(&NativeEntry::NativeCallWrapperLabel(), kNotPatchable);
#endif
__ Comment("CallNativeCFunctionStub return");
// Mark that the isolate is executing Dart code.

View file

@ -185,8 +185,8 @@ void StubCode::GenerateCallNativeCFunctionStub(Assembler* assembler) {
__ movq(CallingConventions::kArg1Reg, RSP);
// Pass pointer to function entrypoint.
__ movq(CallingConventions::kArg2Reg, RBX);
__ LoadExternalLabel(
RAX, &NativeEntry::NativeCallWrapperLabel(), kNotPatchable);
__ movq(RAX, Address(THR, Thread::native_call_wrapper_entry_point_offset()));
__ CallCFunction(RAX);
// Mark that the isolate is executing Dart code.

View file

@ -8,6 +8,7 @@
#include "vm/isolate.h"
#include "vm/lockers.h"
#include "vm/log.h"
#include "vm/native_entry.h"
#include "vm/object.h"
#include "vm/os_thread.h"
#include "vm/profiler.h"

View file

@ -46,6 +46,8 @@ class Zone;
#define CACHED_ADDRESSES_LIST(V) \
V(uword, update_store_buffer_entry_point_, \
StubCode::UpdateStoreBuffer_entry()->EntryPoint(), 0) \
V(uword, native_call_wrapper_entry_point_, \
NativeEntry::NativeCallWrapperEntry(), 0) \
V(RawString**, predefined_symbols_address_, \
Symbols::PredefinedAddress(), NULL) \