Add central bridge for liveedit support
Review URL: http://codereview.chromium.org/607004 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@3891 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
This commit is contained in:
parent
68246ec4a9
commit
3849f08ade
@ -72,6 +72,7 @@ SOURCES = {
|
||||
interpreter-irregexp.cc
|
||||
jsregexp.cc
|
||||
jump-target.cc
|
||||
liveedit.cc
|
||||
log-utils.cc
|
||||
log.cc
|
||||
mark-compact.cc
|
||||
|
@ -31,6 +31,7 @@
|
||||
#include "codegen-inl.h"
|
||||
#include "compiler.h"
|
||||
#include "debug.h"
|
||||
#include "liveedit.h"
|
||||
#include "oprofile-agent.h"
|
||||
#include "prettyprinter.h"
|
||||
#include "register-allocator-inl.h"
|
||||
@ -234,6 +235,7 @@ Handle<Code> CodeGenerator::MakeCodeEpilogue(MacroAssembler* masm,
|
||||
// all the pieces into a Code object. This function is only to be called by
|
||||
// the compiler.cc code.
|
||||
Handle<Code> CodeGenerator::MakeCode(CompilationInfo* info) {
|
||||
LiveEditFunctionTracker live_edit_tracker(info->function());
|
||||
Handle<Script> script = info->script();
|
||||
if (!script->IsUndefined() && !script->source()->IsUndefined()) {
|
||||
int len = String::cast(script->source())->length();
|
||||
@ -245,6 +247,7 @@ Handle<Code> CodeGenerator::MakeCode(CompilationInfo* info) {
|
||||
MacroAssembler masm(NULL, kInitialBufferSize);
|
||||
CodeGenerator cgen(&masm);
|
||||
CodeGeneratorScope scope(&cgen);
|
||||
live_edit_tracker.RecordFunctionScope(info->function()->scope());
|
||||
cgen.Generate(info, PRIMARY);
|
||||
if (cgen.HasStackOverflow()) {
|
||||
ASSERT(!Top::has_pending_exception());
|
||||
@ -253,7 +256,9 @@ Handle<Code> CodeGenerator::MakeCode(CompilationInfo* info) {
|
||||
|
||||
InLoopFlag in_loop = (cgen.loop_nesting() != 0) ? IN_LOOP : NOT_IN_LOOP;
|
||||
Code::Flags flags = Code::ComputeFlags(Code::FUNCTION, in_loop);
|
||||
return MakeCodeEpilogue(cgen.masm(), flags, info);
|
||||
Handle<Code> result = MakeCodeEpilogue(cgen.masm(), flags, info);
|
||||
live_edit_tracker.RecordFunctionCode(result);
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
|
@ -38,6 +38,7 @@
|
||||
#include "rewriter.h"
|
||||
#include "scopes.h"
|
||||
#include "usage-analyzer.h"
|
||||
#include "liveedit.h"
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
@ -429,7 +430,8 @@ Handle<JSFunction> Compiler::BuildBoilerplate(FunctionLiteral* literal,
|
||||
// compiled. These builtins cannot be handled lazily by the parser,
|
||||
// since we have to know if a function uses the special natives
|
||||
// syntax, which is something the parser records.
|
||||
bool allow_lazy = literal->AllowsLazyCompilation();
|
||||
bool allow_lazy = literal->AllowsLazyCompilation() &&
|
||||
!LiveEditFunctionTracker::IsActive();
|
||||
|
||||
// Generate code
|
||||
Handle<Code> code;
|
||||
|
@ -32,6 +32,7 @@
|
||||
#include "full-codegen.h"
|
||||
#include "stub-cache.h"
|
||||
#include "debug.h"
|
||||
#include "liveedit.h"
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
@ -448,6 +449,8 @@ Handle<Code> FullCodeGenerator::MakeCode(CompilationInfo* info) {
|
||||
CodeGenerator::MakeCodePrologue(info);
|
||||
const int kInitialBufferSize = 4 * KB;
|
||||
MacroAssembler masm(NULL, kInitialBufferSize);
|
||||
LiveEditFunctionTracker live_edit_tracker(info->function());
|
||||
|
||||
FullCodeGenerator cgen(&masm);
|
||||
cgen.Generate(info, PRIMARY);
|
||||
if (cgen.HasStackOverflow()) {
|
||||
@ -455,7 +458,9 @@ Handle<Code> FullCodeGenerator::MakeCode(CompilationInfo* info) {
|
||||
return Handle<Code>::null();
|
||||
}
|
||||
Code::Flags flags = Code::ComputeFlags(Code::FUNCTION, NOT_IN_LOOP);
|
||||
return CodeGenerator::MakeCodeEpilogue(&masm, flags, info);
|
||||
Handle<Code> result = CodeGenerator::MakeCodeEpilogue(&masm, flags, info);
|
||||
live_edit_tracker.RecordFunctionCode(result);
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
|
87
src/liveedit.cc
Normal file
87
src/liveedit.cc
Normal file
@ -0,0 +1,87 @@
|
||||
// Copyright 2010 the V8 project authors. All rights reserved.
|
||||
// Redistribution and use in source and binary forms, with or without
|
||||
// modification, are permitted provided that the following conditions are
|
||||
// met:
|
||||
//
|
||||
// * Redistributions of source code must retain the above copyright
|
||||
// notice, this list of conditions and the following disclaimer.
|
||||
// * Redistributions in binary form must reproduce the above
|
||||
// copyright notice, this list of conditions and the following
|
||||
// disclaimer in the documentation and/or other materials provided
|
||||
// with the distribution.
|
||||
// * Neither the name of Google Inc. nor the names of its
|
||||
// contributors may be used to endorse or promote products derived
|
||||
// from this software without specific prior written permission.
|
||||
//
|
||||
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
#include "v8.h"
|
||||
|
||||
#include "liveedit.h"
|
||||
#include "compiler.h"
|
||||
#include "oprofile-agent.h"
|
||||
#include "scopes.h"
|
||||
#include "global-handles.h"
|
||||
#include "debug.h"
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
|
||||
|
||||
class FunctionInfoListener {
|
||||
public:
|
||||
void FunctionStarted(FunctionLiteral* fun) {
|
||||
// Implementation follows.
|
||||
}
|
||||
|
||||
void FunctionDone() {
|
||||
// Implementation follows.
|
||||
}
|
||||
|
||||
void FunctionScope(Scope* scope){
|
||||
// Implementation follows.
|
||||
}
|
||||
|
||||
void FunctionCode(Handle<Code> function_code) {
|
||||
// Implementation follows.
|
||||
}
|
||||
};
|
||||
|
||||
static FunctionInfoListener* active_function_info_listener = NULL;
|
||||
|
||||
LiveEditFunctionTracker::LiveEditFunctionTracker(FunctionLiteral* fun) {
|
||||
if (active_function_info_listener != NULL) {
|
||||
active_function_info_listener->FunctionStarted(fun);
|
||||
}
|
||||
}
|
||||
LiveEditFunctionTracker::~LiveEditFunctionTracker() {
|
||||
if (active_function_info_listener != NULL) {
|
||||
active_function_info_listener->FunctionDone();
|
||||
}
|
||||
}
|
||||
void LiveEditFunctionTracker::RecordFunctionCode(Handle<Code> code) {
|
||||
if (active_function_info_listener != NULL) {
|
||||
active_function_info_listener->FunctionCode(code);
|
||||
}
|
||||
}
|
||||
void LiveEditFunctionTracker::RecordFunctionScope(Scope* scope) {
|
||||
if (active_function_info_listener != NULL) {
|
||||
active_function_info_listener->FunctionScope(scope);
|
||||
}
|
||||
}
|
||||
bool LiveEditFunctionTracker::IsActive() {
|
||||
return active_function_info_listener != NULL;
|
||||
}
|
||||
|
||||
} } // namespace v8::internal
|
78
src/liveedit.h
Normal file
78
src/liveedit.h
Normal file
@ -0,0 +1,78 @@
|
||||
// Copyright 2010 the V8 project authors. All rights reserved.
|
||||
// Redistribution and use in source and binary forms, with or without
|
||||
// modification, are permitted provided that the following conditions are
|
||||
// met:
|
||||
//
|
||||
// * Redistributions of source code must retain the above copyright
|
||||
// notice, this list of conditions and the following disclaimer.
|
||||
// * Redistributions in binary form must reproduce the above
|
||||
// copyright notice, this list of conditions and the following
|
||||
// disclaimer in the documentation and/or other materials provided
|
||||
// with the distribution.
|
||||
// * Neither the name of Google Inc. nor the names of its
|
||||
// contributors may be used to endorse or promote products derived
|
||||
// from this software without specific prior written permission.
|
||||
//
|
||||
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
#ifndef V8_LIVEEDIT_H_
|
||||
#define V8_LIVEEDIT_H_
|
||||
|
||||
|
||||
|
||||
// Live Edit feature implementation.
|
||||
// User should be able to change script on already running VM. This feature
|
||||
// matches hot swap features in other frameworks.
|
||||
//
|
||||
// The basic use-case is when user spots some mistake in function body
|
||||
// from debugger and wishes to change the algorithm without restart.
|
||||
//
|
||||
// A single change always has a form of a simple replacement (in pseudo-code):
|
||||
// script.source[positions, positions+length] = new_string;
|
||||
// Implementation first determines, which function's body includes this
|
||||
// change area. Then both old and new versions of script are fully compiled
|
||||
// in order to analyze, whether the function changed its outer scope
|
||||
// expectations (or number of parameters). If it didn't, function's code is
|
||||
// patched with a newly compiled code. If it did change, enclosing function
|
||||
// gets patched. All inner functions are left untouched, whatever happened
|
||||
// to them in a new script version. However, new version of code will
|
||||
// instantiate newly compiled functions.
|
||||
|
||||
|
||||
#include "compiler.h"
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
|
||||
// This class collects some specific information on structure of functions
|
||||
// in a particular script. It gets called from compiler all the time, but
|
||||
// actually records any data only when liveedit operation is in process;
|
||||
// in any other time this class is very cheap.
|
||||
//
|
||||
// The primary interest of the Tracker is to record function scope structures
|
||||
// in order to analyze whether function code maybe safely patched (with new
|
||||
// code successfully reading existing data from function scopes). The Tracker
|
||||
// also collects compiled function codes.
|
||||
class LiveEditFunctionTracker {
|
||||
public:
|
||||
LiveEditFunctionTracker(FunctionLiteral* fun);
|
||||
~LiveEditFunctionTracker();
|
||||
void RecordFunctionCode(Handle<Code> code);
|
||||
void RecordFunctionScope(Scope* scope);
|
||||
|
||||
static bool IsActive();
|
||||
};
|
||||
|
||||
} } // namespace v8::internal
|
||||
|
||||
#endif /* V*_LIVEEDIT_H_ */
|
@ -308,6 +308,8 @@
|
||||
'../../src/jsregexp.h',
|
||||
'../../src/list-inl.h',
|
||||
'../../src/list.h',
|
||||
'../../src/liveedit.cc',
|
||||
'../../src/liveedit.h',
|
||||
'../../src/log-inl.h',
|
||||
'../../src/log-utils.cc',
|
||||
'../../src/log-utils.h',
|
||||
|
@ -576,6 +576,14 @@
|
||||
RelativePath="..\..\src\list.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\liveedit.cc"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\liveedit.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\log.cc"
|
||||
>
|
||||
|
@ -580,6 +580,14 @@
|
||||
RelativePath="..\..\src\list.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\liveedit.cc"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\liveedit.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\log.cc"
|
||||
>
|
||||
|
@ -577,6 +577,14 @@
|
||||
RelativePath="..\..\src\list.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\liveedit.cc"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\liveedit.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\log.cc"
|
||||
>
|
||||
|
Loading…
Reference in New Issue
Block a user