Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(241)

Unified Diff: extensions/renderer/script_injection_manager.cc

Issue 878513005: Extensions: suspend extension's scripts when V8 is paused (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Fixed ActivityLogPrerenderTest.TestScriptInjected Created 5 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: extensions/renderer/script_injection_manager.cc
diff --git a/extensions/renderer/script_injection_manager.cc b/extensions/renderer/script_injection_manager.cc
index 93862dd04bdfe1109bf23c223ccef4cb734ec90e..51cc6a86add7c9f4bc30bfcffe5c23518cce14ca 100644
--- a/extensions/renderer/script_injection_manager.cc
+++ b/extensions/renderer/script_injection_manager.cc
@@ -242,7 +242,6 @@ ScriptInjectionManager::ScriptInjectionManager(
const ExtensionSet* extensions,
UserScriptSetManager* user_script_set_manager)
: extensions_(extensions),
- injecting_scripts_(false),
user_script_set_manager_(user_script_set_manager),
user_script_set_manager_observer_(this) {
user_script_set_manager_observer_.Add(user_script_set_manager_);
@@ -256,6 +255,22 @@ void ScriptInjectionManager::OnRenderViewCreated(
rvo_helpers_.push_back(new RVOHelper(render_view, this));
}
+void ScriptInjectionManager::OnInjectionFinished(
+ ScriptInjection* injection,
+ scoped_refptr<ScriptsRunInfo> scripts_run_info) {
+ blink::WebFrame* frame = injection->web_frame();
+ UserScript::RunLocation run_location = injection->run_location();
+
+ ScopedVector<ScriptInjection>::iterator it;
+ for (it = running_injections_.begin(); it != running_injections_.end(); ++it){
+ running_injections_.erase(it);
+ break;
+ }
+
+ if (scripts_run_info && scripts_run_info->HasOneRef() && IsFrameValid(frame))
Devlin 2015/02/25 18:02:15 ref counted lifetimes are already somewhat Evil.
kozy 2015/02/27 17:32:28 I've removed ref counted Scripts Run Info and retu
Devlin 2015/02/27 18:25:32 Fair enough. More than anything else, I'd want to
kozy 2015/02/28 15:23:21 I've added _BlockedScriptCount metrics to ScriptsR
+ scripts_run_info->LogRun(frame, run_location);
+}
+
void ScriptInjectionManager::OnUserScriptsUpdated(
const std::set<std::string>& changed_extensions,
const std::vector<UserScript*>& scripts) {
@@ -267,13 +282,6 @@ void ScriptInjectionManager::OnUserScriptsUpdated(
else
++iter;
}
-
- // If we are currently injecting scripts, we need to make a note that these
- // extensions were updated.
- if (injecting_scripts_) {
- invalidated_while_injecting_.insert(changed_extensions.begin(),
- changed_extensions.end());
- }
}
void ScriptInjectionManager::RemoveObserver(RVOHelper* helper) {
@@ -337,30 +345,21 @@ void ScriptInjectionManager::StartInjectScripts(
frame_statuses_[frame] = run_location;
- // If a content script injects blocking code (such as a javascript alert()),
- // then there is a chance that we are running in a nested message loop, and
- // shouldn't inject scripts right now (to avoid conflicts).
- if (!injecting_scripts_) {
+ InjectScripts(frame, run_location);
+ // As above, we might have been blocked, but that means that, in the mean
Devlin 2015/02/25 18:02:15 Isn't the point of this patch that executing scrip
kozy 2015/02/27 17:32:28 Done.
+ // time, it's possible the frame advanced. Inject any scripts for run
+ // locations that were registered, but never ran.
+ while ((iter = frame_statuses_.find(frame)) != frame_statuses_.end() &&
+ iter->second > run_location) {
+ run_location = NextRunLocation(run_location);
+ DCHECK_LE(run_location, UserScript::DOCUMENT_IDLE);
InjectScripts(frame, run_location);
- // As above, we might have been blocked, but that means that, in the mean
- // time, it's possible the frame advanced. Inject any scripts for run
- // locations that were registered, but never ran.
- while ((iter = frame_statuses_.find(frame)) != frame_statuses_.end() &&
- iter->second > run_location) {
- run_location = NextRunLocation(run_location);
- DCHECK_LE(run_location, UserScript::DOCUMENT_IDLE);
- InjectScripts(frame, run_location);
- }
}
}
void ScriptInjectionManager::InjectScripts(
blink::WebFrame* frame,
UserScript::RunLocation run_location) {
- DCHECK(!injecting_scripts_);
- DCHECK(invalidated_while_injecting_.empty());
- base::AutoReset<bool>(&injecting_scripts_, true);
-
// Find any injections that want to run on the given frame.
// We create a separate vector for these because there is a chance that
// injected scripts can block, which can create a nested message loop. When
@@ -384,7 +383,7 @@ void ScriptInjectionManager::InjectScripts(
user_script_set_manager_->GetAllInjections(
&frame_injections, frame, tab_id, run_location);
- ScriptsRunInfo scripts_run_info;
+ scoped_refptr<ScriptsRunInfo> scripts_run_info(new ScriptsRunInfo());
for (ScopedVector<ScriptInjection>::iterator iter = frame_injections.begin();
iter != frame_injections.end();) {
// If a blocking script was injected, there is potentially a possibility
@@ -395,24 +394,30 @@ void ScriptInjectionManager::InjectScripts(
const std::string& extension_id = (*iter)->host_id().id();
scoped_ptr<ExtensionInjectionHost> extension_injection_host =
GetExtensionInjectionHost(extension_id, extensions_);
- // Try to inject the script if the extension is not "dirty" (invalidated by
- // an update). If the injection does not finish (i.e., it is waiting for
- // permission), add it to the list of pending injections.
- if (invalidated_while_injecting_.count(extension_id) == 0 &&
- !(*iter)->TryToInject(run_location,
- extension_injection_host.get(),
- &scripts_run_info)) {
- pending_injections_.insert(pending_injections_.begin(), *iter);
+ // Try to inject the script. If the injection does not finish
+ // (i.e., it is waiting for permission), add it to the list of pending
+ // injections. If the injection does not finished, add it to the list of
+ // running injections.
+ ScriptInjection* injection = *iter;
+ injection->SetScriptInjectionManager(this);
+ if (!injection->TryToInject(run_location,
+ extension_injection_host.get(),
+ scripts_run_info)) {
+ pending_injections_.insert(pending_injections_.begin(), injection);
+ iter = frame_injections.weak_erase(iter);
+ } else if (!injection->is_complete()) {
+ running_injections_.insert(running_injections_.begin(), injection);
iter = frame_injections.weak_erase(iter);
} else {
++iter;
}
}
- if (IsFrameValid(frame))
- scripts_run_info.LogRun(frame, run_location);
-
- invalidated_while_injecting_.clear();
+ frame_injections.clear();
+ // If injection executes synchronously in OnInjectionFinished handler we
+ // will have two refs to scripts run info and we need call here LogRun
+ if (scripts_run_info && scripts_run_info->HasOneRef() && IsFrameValid(frame))
+ scripts_run_info->LogRun(frame, run_location);
}
void ScriptInjectionManager::HandleExecuteCode(
@@ -441,18 +446,28 @@ void ScriptInjectionManager::HandleExecuteCode(
static_cast<UserScript::RunLocation>(params.run_at),
ExtensionHelper::Get(render_view)->tab_id()));
- ScriptsRunInfo scripts_run_info;
+ scoped_refptr<ScriptsRunInfo> scripts_run_info(new ScriptsRunInfo());
FrameStatusMap::const_iterator iter = frame_statuses_.find(main_frame);
+ blink::WebFrame* frame = injection->web_frame();
+ UserScript::RunLocation run_location = injection->run_location();
+
scoped_ptr<ExtensionInjectionHost> extension_injection_host =
GetExtensionInjectionHost(injection->host_id().id(), extensions_);
-
+ injection->SetScriptInjectionManager(this);
if (!injection->TryToInject(
iter == frame_statuses_.end() ? UserScript::UNDEFINED : iter->second,
extension_injection_host.get(),
- &scripts_run_info)) {
+ scripts_run_info)) {
pending_injections_.push_back(injection.release());
+ } else if (!injection->is_complete()) {
+ running_injections_.push_back(injection.release());
+ } else {
+ injection = NULL;
}
+
+ if (scripts_run_info && scripts_run_info->HasOneRef() && IsFrameValid(frame))
+ scripts_run_info->LogRun(frame, run_location);
}
void ScriptInjectionManager::HandleExecuteDeclarativeScript(
@@ -474,12 +489,23 @@ void ScriptInjectionManager::HandleExecuteDeclarativeScript(
url,
extension);
if (injection.get()) {
- ScriptsRunInfo scripts_run_info;
+ scoped_refptr<ScriptsRunInfo> scripts_run_info(new ScriptsRunInfo());
+ injection->SetScriptInjectionManager(this);
+
+ blink::WebFrame* frame = injection->web_frame();
+ UserScript::RunLocation run_location = injection->run_location();
+
// TODO(markdittmer): Use return value of TryToInject for error handling.
- injection->TryToInject(UserScript::BROWSER_DRIVEN,
- extension_injection_host.get(),
- &scripts_run_info);
- scripts_run_info.LogRun(web_frame, UserScript::BROWSER_DRIVEN);
+ if (injection->TryToInject(UserScript::BROWSER_DRIVEN,
+ extension_injection_host.get(),
+ scripts_run_info)) {
+ if (!injection->is_complete())
+ running_injections_.push_back(injection.release());
+ }
+ injection = NULL;
+ if (scripts_run_info && scripts_run_info->HasOneRef()
+ && IsFrameValid(frame))
+ scripts_run_info->LogRun(frame, run_location);
}
}
@@ -501,12 +527,13 @@ void ScriptInjectionManager::HandlePermitScriptInjection(int64 request_id) {
scoped_ptr<ScriptInjection> injection(*iter);
pending_injections_.weak_erase(iter);
- ScriptsRunInfo scripts_run_info;
+ injection->SetScriptInjectionManager(this);
+
scoped_ptr<ExtensionInjectionHost> extension_injection_host =
GetExtensionInjectionHost(injection->host_id().id(), extensions_);
- if (injection->OnPermissionGranted(extension_injection_host.get(),
- &scripts_run_info)) {
- scripts_run_info.LogRun(injection->web_frame(), UserScript::RUN_DEFERRED);
+ if (injection->OnPermissionGranted(extension_injection_host.get())) {
+ if (!injection->is_complete())
+ running_injections_.push_back(injection.Pass());
}
}

Powered by Google App Engine
This is Rietveld 408576698