Copy JavaScript execution to RenderFrame, switch easy cases to use it.

BUG=304341
TEST=no change

Review URL: https://codereview.chromium.org/188893005

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@256460 0039d316-1c4b-4281-b951-d872f2087c98
diff --git a/chrome/browser/captive_portal/captive_portal_browsertest.cc b/chrome/browser/captive_portal/captive_portal_browsertest.cc
index aecf168..9f4ce844 100644
--- a/chrome/browser/captive_portal/captive_portal_browsertest.cc
+++ b/chrome/browser/captive_portal/captive_portal_browsertest.cc
@@ -38,7 +38,7 @@
 #include "content/public/browser/notification_registrar.h"
 #include "content/public/browser/notification_service.h"
 #include "content/public/browser/notification_types.h"
-#include "content/public/browser/render_view_host.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/common/url_constants.h"
 #include "content/test/net/url_request_failed_job.h"
@@ -1317,10 +1317,9 @@
   ASSERT_TRUE(IsLoginTab(browser->tab_strip_model()->GetActiveWebContents()));
 
   // Do the navigation.
-  content::RenderViewHost* render_view_host =
-      tab_strip_model->GetActiveWebContents()->GetRenderViewHost();
-  render_view_host->ExecuteJavascriptInWebFrame(
-      base::string16(), base::ASCIIToUTF16("submitForm()"));
+  content::RenderFrameHost* render_frame_host =
+      tab_strip_model->GetActiveWebContents()->GetMainFrame();
+  render_frame_host->ExecuteJavaScript(base::ASCIIToUTF16("submitForm()"));
 
   portal_observer.WaitForResults(1);
   navigation_observer.WaitForNavigations(1);
@@ -1365,10 +1364,9 @@
   ASSERT_TRUE(IsLoginTab(tab_strip_model->GetWebContentsAt(login_tab_index)));
 
   // Trigger a navigation.
-  content::RenderViewHost* render_view_host =
-      tab_strip_model->GetActiveWebContents()->GetRenderViewHost();
-  render_view_host->ExecuteJavascriptInWebFrame(
-      base::string16(), base::ASCIIToUTF16("submitForm()"));
+  content::RenderFrameHost* render_frame_host =
+      tab_strip_model->GetActiveWebContents()->GetMainFrame();
+  render_frame_host->ExecuteJavaScript(base::ASCIIToUTF16("submitForm()"));
 
   portal_observer.WaitForResults(1);
 
@@ -1719,11 +1717,9 @@
   CaptivePortalObserver portal_observer(browser()->profile());
 
   TabStripModel* tab_strip_model = browser()->tab_strip_model();
-  content::RenderViewHost* render_view_host =
-      tab_strip_model->GetActiveWebContents()->GetRenderViewHost();
-  render_view_host->ExecuteJavascriptInWebFrame(
-      base::string16(),
-      base::ASCIIToUTF16("submitForm()"));
+  content::RenderFrameHost* render_frame_host =
+      tab_strip_model->GetActiveWebContents()->GetMainFrame();
+  render_frame_host->ExecuteJavaScript(base::ASCIIToUTF16("submitForm()"));
 
   // The captive portal tab navigation will trigger a captive portal check,
   // and reloading the original tab will bring up the interstitial page again,
diff --git a/chrome/browser/chromeos/login/screen_locker_tester.cc b/chrome/browser/chromeos/login/screen_locker_tester.cc
index 4372f7f..7b8d1a2 100644
--- a/chrome/browser/chromeos/login/screen_locker_tester.cc
+++ b/chrome/browser/chromeos/login/screen_locker_tester.cc
@@ -15,6 +15,7 @@
 #include "chrome/browser/chromeos/login/screen_locker.h"
 #include "chrome/browser/chromeos/login/webui_screen_locker.h"
 #include "chrome/test/base/ui_test_utils.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/browser/web_ui.h"
@@ -119,8 +120,7 @@
 };
 
 void WebUIScreenLockerTester::SetPassword(const std::string& password) {
-  RenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(),
+  webui()->GetWebContents()->GetMainFrame()->ExecuteJavaScript(
       base::ASCIIToUTF16(base::StringPrintf(
           "$('pod-row').pods[0].passwordElement.value = '%s';",
           password.c_str())));
diff --git a/chrome/browser/devtools/devtools_window.cc b/chrome/browser/devtools/devtools_window.cc
index 9d04732..b07386c0 100644
--- a/chrome/browser/devtools/devtools_window.cc
+++ b/chrome/browser/devtools/devtools_window.cc
@@ -1435,8 +1435,7 @@
       "\", \"" +
       SkColorToRGBAString(tp->GetColor(ThemeProperties::COLOR_BOOKMARK_TEXT)) +
       "\")");
-  web_contents_->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(), base::ASCIIToUTF16(command));
+  web_contents_->GetMainFrame()->ExecuteJavaScript(base::ASCIIToUTF16(command));
 }
 
 void DevToolsWindow::AddDevToolsExtensionsToClient() {
@@ -1498,8 +1497,7 @@
   }
   base::string16 javascript =
       base::ASCIIToUTF16(function_name + "(" + params + ");");
-  web_contents_->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(), javascript);
+  web_contents_->GetMainFrame()->ExecuteJavaScript(javascript);
 }
 
 void DevToolsWindow::UpdateBrowserToolbar() {
diff --git a/chrome/browser/download/download_browsertest.cc b/chrome/browser/download/download_browsertest.cc
index 2c11522..e1ec1c9d 100644
--- a/chrome/browser/download/download_browsertest.cc
+++ b/chrome/browser/download/download_browsertest.cc
@@ -68,6 +68,7 @@
 #include "content/public/browser/download_save_info.h"
 #include "content/public/browser/download_url_parameters.h"
 #include "content/public/browser/notification_source.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/browser/resource_context.h"
 #include "content/public/browser/web_contents.h"
@@ -2359,10 +2360,9 @@
       content::NOTIFICATION_NAV_ENTRY_COMMITTED,
       content::Source<content::NavigationController>(
           &web_contents->GetController()));
-  content::RenderViewHost* render_view_host = web_contents->GetRenderViewHost();
-  ASSERT_TRUE(render_view_host != NULL);
-  render_view_host->ExecuteJavascriptInWebFrame(
-        base::string16(), base::ASCIIToUTF16("SubmitForm()"));
+  content::RenderFrameHost* render_frame_host = web_contents->GetMainFrame();
+  ASSERT_TRUE(render_frame_host != NULL);
+  render_frame_host->ExecuteJavaScript(base::ASCIIToUTF16("SubmitForm()"));
   observer.Wait();
   EXPECT_EQ(jpeg_url, web_contents->GetURL());
 
diff --git a/chrome/browser/errorpage_browsertest.cc b/chrome/browser/errorpage_browsertest.cc
index 47c00f8..9a60d1cb 100644
--- a/chrome/browser/errorpage_browsertest.cc
+++ b/chrome/browser/errorpage_browsertest.cc
@@ -21,6 +21,7 @@
 #include "chrome/test/base/in_process_browser_test.h"
 #include "chrome/test/base/ui_test_utils.h"
 #include "content/public/browser/notification_service.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/browser/web_contents_observer.h"
@@ -523,8 +524,7 @@
     content::WindowedNotificationObserver load_observer(
         content::NOTIFICATION_LOAD_STOP,
         content::Source<NavigationController>(&wc->GetController()));
-    wc->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-        base::string16(), base::ASCIIToUTF16(script));
+    wc->GetMainFrame()->ExecuteJavaScript(base::ASCIIToUTF16(script));
     load_observer.Wait();
 
     // Ensure we saw the expected failure.
@@ -544,8 +544,7 @@
     content::WindowedNotificationObserver load_observer(
         content::NOTIFICATION_LOAD_STOP,
         content::Source<NavigationController>(&wc->GetController()));
-    wc->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-        base::string16(), base::ASCIIToUTF16(script));
+    wc->GetMainFrame()->ExecuteJavaScript(base::ASCIIToUTF16(script));
     load_observer.Wait();
   }
 
@@ -556,8 +555,7 @@
     content::WindowedNotificationObserver load_observer(
         content::NOTIFICATION_LOAD_STOP,
         content::Source<NavigationController>(&wc->GetController()));
-    wc->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-        base::string16(), base::ASCIIToUTF16(script));
+    wc->GetMainFrame()->ExecuteJavaScript(base::ASCIIToUTF16(script));
     load_observer.Wait();
 
     EXPECT_EQ(fail_url, fail_observer.fail_url());
diff --git a/chrome/browser/extensions/alert_apitest.cc b/chrome/browser/extensions/alert_apitest.cc
index ac78caa2..0b8cc6bb 100644
--- a/chrome/browser/extensions/alert_apitest.cc
+++ b/chrome/browser/extensions/alert_apitest.cc
@@ -9,7 +9,7 @@
 #include "chrome/browser/ui/app_modal_dialogs/app_modal_dialog.h"
 #include "chrome/browser/ui/browser.h"
 #include "chrome/test/base/ui_test_utils.h"
-#include "content/public/browser/render_view_host.h"
+#include "content/public/browser/render_frame_host.h"
 #include "extensions/browser/extension_system.h"
 #include "extensions/browser/process_manager.h"
 #include "extensions/common/extension.h"
@@ -22,7 +22,7 @@
       extensions::ExtensionSystem::Get(browser()->profile())->
           process_manager()->GetBackgroundHostForExtension(extension->id());
   ASSERT_TRUE(host);
-  host->render_view_host()->ExecuteJavascriptInWebFrame(base::string16(),
+  host->host_contents()->GetMainFrame()->ExecuteJavaScript(
       base::ASCIIToUTF16("alert('This should not crash.');"));
 
   AppModalDialog* alert = ui_test_utils::WaitForAppModalDialog();
diff --git a/chrome/browser/extensions/api/media_galleries_private/media_galleries_private_apitest.cc b/chrome/browser/extensions/api/media_galleries_private/media_galleries_private_apitest.cc
index 10b94c8..83389199 100644
--- a/chrome/browser/extensions/api/media_galleries_private/media_galleries_private_apitest.cc
+++ b/chrome/browser/extensions/api/media_galleries_private/media_galleries_private_apitest.cc
@@ -14,6 +14,7 @@
 #include "components/storage_monitor/storage_info.h"
 #include "components/storage_monitor/storage_monitor.h"
 #include "components/storage_monitor/test_storage_monitor.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/test/browser_test_utils.h"
@@ -80,8 +81,7 @@
                       const std::string& js_command,
                       const std::string& ok_message) {
     ExtensionTestMessageListener listener(ok_message, false  /* no reply */);
-    host->ExecuteJavascriptInWebFrame(base::string16(),
-                                      base::ASCIIToUTF16(js_command));
+    host->GetMainFrame()->ExecuteJavaScript(base::ASCIIToUTF16(js_command));
     EXPECT_TRUE(listener.WaitUntilSatisfied());
   }
 
diff --git a/chrome/browser/extensions/api/media_galleries_private/media_galleries_watch_apitest.cc b/chrome/browser/extensions/api/media_galleries_private/media_galleries_watch_apitest.cc
index 9564818..7c79c36 100644
--- a/chrome/browser/extensions/api/media_galleries_private/media_galleries_watch_apitest.cc
+++ b/chrome/browser/extensions/api/media_galleries_private/media_galleries_watch_apitest.cc
@@ -15,6 +15,7 @@
 #include "chrome/browser/media_galleries/media_galleries_test_util.h"
 #include "chrome/common/chrome_paths.h"
 #include "chrome/common/chrome_switches.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "extensions/browser/extension_system.h"
 #include "extensions/common/extension.h"
@@ -89,8 +90,7 @@
                               const std::string& js_command,
                               const std::string& ok_message) {
     ExtensionTestMessageListener listener(ok_message, false);
-    host->ExecuteJavascriptInWebFrame(base::string16(),
-                                      base::ASCIIToUTF16(js_command));
+    host->GetMainFrame()->ExecuteJavaScript(base::ASCIIToUTF16(js_command));
     EXPECT_TRUE(listener.WaitUntilSatisfied());
   }
 
diff --git a/chrome/browser/extensions/api/push_messaging/push_messaging_canary_test.cc b/chrome/browser/extensions/api/push_messaging/push_messaging_canary_test.cc
index aa34756..6aee2920 100644
--- a/chrome/browser/extensions/api/push_messaging/push_messaging_canary_test.cc
+++ b/chrome/browser/extensions/api/push_messaging/push_messaging_canary_test.cc
@@ -14,7 +14,7 @@
 #include "chrome/browser/ui/tabs/tab_strip_model.h"
 #include "chrome/common/chrome_switches.h"
 #include "chrome/test/base/ui_test_utils.h"
-#include "content/public/browser/render_view_host.h"
+#include "content/public/browser/render_frame_host.h"
 #include "extensions/common/extension_set.h"
 #include "net/dns/mock_host_resolver.h"
 
@@ -160,8 +160,8 @@
       "startTestWithCredentials('%s', '%s', '%s');",
       client_id.c_str(), client_secret.c_str(), refresh_token.c_str()));
 
-  browser()->tab_strip_model()->GetActiveWebContents()->GetRenderViewHost()->
-      ExecuteJavascriptInWebFrame(base::string16(), script_string);
+  browser()->tab_strip_model()->GetActiveWebContents()->GetMainFrame()->
+      ExecuteJavaScript(script_string);
 
   EXPECT_TRUE(catcher.GetNextResult()) << catcher.message();
 }
diff --git a/chrome/browser/extensions/api/system_storage/system_storage_eject_apitest.cc b/chrome/browser/extensions/api/system_storage/system_storage_eject_apitest.cc
index b0a50bb..eeb74d95 100644
--- a/chrome/browser/extensions/api/system_storage/system_storage_eject_apitest.cc
+++ b/chrome/browser/extensions/api/system_storage/system_storage_eject_apitest.cc
@@ -14,6 +14,7 @@
 #include "components/storage_monitor/storage_info.h"
 #include "components/storage_monitor/storage_monitor.h"
 #include "components/storage_monitor/test_storage_monitor.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/test/test_utils.h"
 #include "extensions/browser/extension_system.h"
@@ -52,8 +53,7 @@
                                const std::string& js_command,
                                const std::string& ok_message) {
     ExtensionTestMessageListener listener(ok_message, false);
-    host->ExecuteJavascriptInWebFrame(base::string16(),
-                                      base::ASCIIToUTF16(js_command));
+    host->GetMainFrame()->ExecuteJavaScript(base::ASCIIToUTF16(js_command));
     EXPECT_TRUE(listener.WaitUntilSatisfied());
   }
 
diff --git a/chrome/browser/extensions/api/web_navigation/web_navigation_apitest.cc b/chrome/browser/extensions/api/web_navigation/web_navigation_apitest.cc
index c523d5a9..6b7cc87 100644
--- a/chrome/browser/extensions/api/web_navigation/web_navigation_apitest.cc
+++ b/chrome/browser/extensions/api/web_navigation/web_navigation_apitest.cc
@@ -27,6 +27,7 @@
 #include "chrome/browser/ui/tabs/tab_strip_model.h"
 #include "chrome/test/base/ui_test_utils.h"
 #include "content/public/browser/browser_thread.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_process_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/browser/resource_controller.h"
@@ -183,8 +184,7 @@
     if (validated_url != delay_url_ || !rvh_)
       return;
 
-    rvh_->ExecuteJavascriptInWebFrame(base::string16(),
-                                      base::UTF8ToUTF16(script_));
+    rvh_->GetMainFrame()->ExecuteJavaScript(base::UTF8ToUTF16(script_));
     script_was_executed_ = true;
   }
 
diff --git a/chrome/browser/extensions/webstore_installer_test.cc b/chrome/browser/extensions/webstore_installer_test.cc
index d43b362..fdc4d4a 100644
--- a/chrome/browser/extensions/webstore_installer_test.cc
+++ b/chrome/browser/extensions/webstore_installer_test.cc
@@ -21,7 +21,7 @@
 #include "content/public/browser/notification_registrar.h"
 #include "content/public/browser/notification_service.h"
 #include "content/public/browser/notification_types.h"
-#include "content/public/browser/render_view_host.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/test/browser_test_utils.h"
 #include "net/base/host_port_pair.h"
@@ -120,8 +120,6 @@
     const std::string& test_function_name) {
   std::string script = base::StringPrintf(
       "%s('%s')", test_function_name.c_str(), test_gallery_url_.c_str());
-  browser()->tab_strip_model()->GetActiveWebContents()->GetRenderViewHost()->
-      ExecuteJavascriptInWebFrame(
-          base::UTF8ToUTF16(std::string()),
-          base::UTF8ToUTF16(script));
+  browser()->tab_strip_model()->GetActiveWebContents()->GetMainFrame()->
+      ExecuteJavaScript(base::UTF8ToUTF16(script));
 }
diff --git a/chrome/browser/geolocation/geolocation_browsertest.cc b/chrome/browser/geolocation/geolocation_browsertest.cc
index dd8e659..8b5c138 100644
--- a/chrome/browser/geolocation/geolocation_browsertest.cc
+++ b/chrome/browser/geolocation/geolocation_browsertest.cc
@@ -27,6 +27,7 @@
 #include "content/public/browser/navigation_controller.h"
 #include "content/public/browser/notification_details.h"
 #include "content/public/browser/notification_service.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/test/browser_test_utils.h"
@@ -89,8 +90,7 @@
       "window.domAutomationController.setAutomationId(0);"
       "window.domAutomationController.send(addIFrame(%d, \"%s\"));",
       iframe_id, url.spec().c_str()));
-  web_contents->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(), base::UTF8ToUTF16(script));
+  web_contents->GetMainFrame()->ExecuteJavaScript(base::UTF8ToUTF16(script));
   content::RunMessageLoop();
 
   EXPECT_EQ(base::StringPrintf("\"%d\"", iframe_id), javascript_response_);
diff --git a/chrome/browser/prerender/prerender_browsertest.cc b/chrome/browser/prerender/prerender_browsertest.cc
index a487f269..4aeea62e 100644
--- a/chrome/browser/prerender/prerender_browsertest.cc
+++ b/chrome/browser/prerender/prerender_browsertest.cc
@@ -65,6 +65,7 @@
 #include "content/public/browser/navigation_controller.h"
 #include "content/public/browser/navigation_entry.h"
 #include "content/public/browser/notification_service.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_process_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/browser/site_instance.h"
@@ -96,6 +97,7 @@
 using content::NavigationController;
 using content::OpenURLParams;
 using content::Referrer;
+using content::RenderFrameHost;
 using content::RenderViewHost;
 using content::RenderWidgetHost;
 using content::TestNavigationObserver;
@@ -1186,18 +1188,14 @@
   }
 
   void RemoveLinkElement(int i) const {
-    GetActiveWebContents()->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-            base::string16(),
-            base::ASCIIToUTF16(base::StringPrintf("RemoveLinkElement(%d)", i)));
+    GetActiveWebContents()->GetMainFrame()->ExecuteJavaScript(
+        base::ASCIIToUTF16(base::StringPrintf("RemoveLinkElement(%d)", i)));
   }
 
   void ClickToNextPageAfterPrerender() {
     TestNavigationObserver nav_observer(GetActiveWebContents());
-    RenderViewHost* render_view_host =
-        GetActiveWebContents()->GetRenderViewHost();
-    render_view_host->ExecuteJavascriptInWebFrame(
-        base::string16(),
-        base::ASCIIToUTF16("ClickOpenLink()"));
+    RenderFrameHost* render_frame_host = GetActiveWebContents()->GetMainFrame();
+    render_frame_host->ExecuteJavaScript(base::ASCIIToUTF16("ClickOpenLink()"));
     nav_observer.Wait();
   }
 
@@ -1454,10 +1452,8 @@
   void AddPrerender(const GURL& url, int index) {
     std::string javascript = base::StringPrintf(
         "AddPrerender('%s', %d)", url.spec().c_str(), index);
-    RenderViewHost* render_view_host =
-        GetActiveWebContents()->GetRenderViewHost();
-    render_view_host->ExecuteJavascriptInWebFrame(
-        base::string16(), base::ASCIIToUTF16(javascript));
+    RenderFrameHost* render_frame_host = GetActiveWebContents()->GetMainFrame();
+    render_frame_host->ExecuteJavaScript(base::ASCIIToUTF16(javascript));
   }
 
   // Returns a string for pattern-matching TaskManager tab entries.
@@ -1591,8 +1587,7 @@
                          const GURL& ping_url,
                          bool new_web_contents) const {
     WebContents* web_contents = GetActiveWebContents();
-    RenderViewHost* render_view_host =
-        GetActiveWebContents()->GetRenderViewHost();
+    RenderFrameHost* render_frame_host = web_contents->GetMainFrame();
     // Extra arguments in JS are ignored.
     std::string javascript = base::StringPrintf(
         "%s('%s', '%s')", javascript_function_name.c_str(),
@@ -1600,14 +1595,12 @@
 
     if (new_web_contents) {
       NewTabNavigationOrSwapObserver observer;
-      render_view_host->ExecuteJavascriptInWebFrame(
-          base::string16(), base::ASCIIToUTF16(javascript));
+      render_frame_host->ExecuteJavaScript(base::ASCIIToUTF16(javascript));
       observer.Wait();
     } else {
       NavigationOrSwapObserver observer(current_browser()->tab_strip_model(),
                                         web_contents);
-      render_view_host->ExecuteJavascriptInWebFrame(
-          base::string16(), base::ASCIIToUTF16(javascript));
+      render_frame_host->ExecuteJavaScript(base::ASCIIToUTF16(javascript));
       observer.Wait();
     }
   }
diff --git a/chrome/browser/safe_browsing/safe_browsing_blocking_page_test.cc b/chrome/browser/safe_browsing/safe_browsing_blocking_page_test.cc
index 0f994de..5d1b6d1 100644
--- a/chrome/browser/safe_browsing/safe_browsing_blocking_page_test.cc
+++ b/chrome/browser/safe_browsing/safe_browsing_blocking_page_test.cc
@@ -31,6 +31,7 @@
 #include "content/public/browser/interstitial_page.h"
 #include "content/public/browser/navigation_controller.h"
 #include "content/public/browser/notification_types.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/browser/web_contents_view.h"
@@ -589,8 +590,7 @@
     // We don't use ExecuteScriptAndGetValue for this one, since clicking
     // the button/link may navigate away before the injected javascript can
     // reply, hanging the test.
-    rvh->ExecuteJavascriptInWebFrame(
-        base::string16(),
+    rvh->GetMainFrame()->ExecuteJavaScript(
         base::ASCIIToUTF16(
             "document.getElementById('" + node_id + "').click();\n"));
     return true;
diff --git a/chrome/browser/ui/browser_browsertest.cc b/chrome/browser/ui/browser_browsertest.cc
index 99f4d66..49a5837 100644
--- a/chrome/browser/ui/browser_browsertest.cc
+++ b/chrome/browser/ui/browser_browsertest.cc
@@ -61,6 +61,7 @@
 #include "content/public/browser/interstitial_page_delegate.h"
 #include "content/public/browser/navigation_entry.h"
 #include "content/public/browser/notification_service.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_process_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/browser/render_widget_host_view.h"
@@ -418,8 +419,7 @@
   EXPECT_EQ(0, browser()->tab_strip_model()->active_index());
   WebContents* second_tab = browser()->tab_strip_model()->GetWebContentsAt(1);
   ASSERT_TRUE(second_tab);
-  second_tab->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(),
+  second_tab->GetMainFrame()->ExecuteJavaScript(
       ASCIIToUTF16("alert('Activate!');"));
   AppModalDialog* alert = ui_test_utils::WaitForAppModalDialog();
   alert->CloseModalDialog();
@@ -481,8 +481,7 @@
   // even if the renderer tries to synchronously create more.
   // See http://crbug.com/312490.
   WebContents* contents = browser()->tab_strip_model()->GetActiveWebContents();
-  contents->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(),
+  contents->GetMainFrame()->ExecuteJavaScript(
       ASCIIToUTF16("alert('one'); alert('two');"));
   AppModalDialog* alert = ui_test_utils::WaitForAppModalDialog();
   EXPECT_TRUE(alert->IsValid());
@@ -508,8 +507,7 @@
 
   // Start a navigation to trigger the beforeunload dialog.
   WebContents* contents = browser()->tab_strip_model()->GetActiveWebContents();
-  contents->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(),
+  contents->GetMainFrame()->ExecuteJavaScript(
       ASCIIToUTF16("window.location.href = 'data:text/html,foo'"));
   AppModalDialog* alert = ui_test_utils::WaitForAppModalDialog();
   EXPECT_TRUE(alert->IsValid());
@@ -545,9 +543,8 @@
       browser()->tab_strip_model()->GetActiveWebContents()->IsLoading());
 
   // Clear the beforeunload handler so the test can easily exit.
-  browser()->tab_strip_model()->GetActiveWebContents()->GetRenderViewHost()->
-      ExecuteJavascriptInWebFrame(base::string16(),
-                                  ASCIIToUTF16("onbeforeunload=null;"));
+  browser()->tab_strip_model()->GetActiveWebContents()->GetMainFrame()->
+      ExecuteJavaScript(ASCIIToUTF16("onbeforeunload=null;"));
 }
 
 class RedirectObserver : public content::WebContentsObserver {
@@ -706,9 +703,8 @@
   EXPECT_EQ(url, browser()->toolbar_model()->GetURL());
 
   // Clear the beforeunload handler so the test can easily exit.
-  browser()->tab_strip_model()->GetActiveWebContents()->GetRenderViewHost()->
-      ExecuteJavascriptInWebFrame(base::string16(),
-                                  ASCIIToUTF16("onbeforeunload=null;"));
+  browser()->tab_strip_model()->GetActiveWebContents()->GetMainFrame()->
+      ExecuteJavaScript(ASCIIToUTF16("onbeforeunload=null;"));
 }
 
 // Crashy on mac.  http://crbug.com/38522  Crashy on win too (after 3 years).
@@ -723,16 +719,14 @@
 // Test for crbug.com/11647.  A page closed with window.close() should not have
 // two beforeunload dialogs shown.
 IN_PROC_BROWSER_TEST_F(BrowserTest, MAYBE_SingleBeforeUnloadAfterWindowClose) {
-  browser()->tab_strip_model()->GetActiveWebContents()->GetRenderViewHost()->
-      ExecuteJavascriptInWebFrame(base::string16(),
-                                  ASCIIToUTF16(kOpenNewBeforeUnloadPage));
+  browser()->tab_strip_model()->GetActiveWebContents()->GetMainFrame()->
+      ExecuteJavaScript(ASCIIToUTF16(kOpenNewBeforeUnloadPage));
 
   // Close the new window with JavaScript, which should show a single
   // beforeunload dialog.  Then show another alert, to make it easy to verify
   // that a second beforeunload dialog isn't shown.
-  browser()->tab_strip_model()->GetWebContentsAt(0)->GetRenderViewHost()->
-      ExecuteJavascriptInWebFrame(base::string16(),
-                                  ASCIIToUTF16("w.close(); alert('bar');"));
+  browser()->tab_strip_model()->GetWebContentsAt(0)->GetMainFrame()->
+      ExecuteJavaScript(ASCIIToUTF16("w.close(); alert('bar');"));
   AppModalDialog* alert = ui_test_utils::WaitForAppModalDialog();
   alert->native_dialog()->AcceptAppModalDialog();
 
@@ -888,8 +882,7 @@
   content::WindowedNotificationObserver nav_observer(
       content::NOTIFICATION_NAV_ENTRY_COMMITTED,
       content::NotificationService::AllSources());
-  oldtab->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(), ASCIIToUTF16(redirect_popup));
+  oldtab->GetMainFrame()->ExecuteJavaScript(ASCIIToUTF16(redirect_popup));
 
   // Wait for popup window to appear and finish navigating.
   popup_observer.Wait();
@@ -922,8 +915,7 @@
   content::WindowedNotificationObserver nav_observer2(
       content::NOTIFICATION_NAV_ENTRY_COMMITTED,
       content::NotificationService::AllSources());
-  oldtab->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(), ASCIIToUTF16(refresh_popup));
+  oldtab->GetMainFrame()->ExecuteJavaScript(ASCIIToUTF16(refresh_popup));
 
   // Wait for popup window to appear and finish navigating.
   popup_observer2.Wait();
@@ -976,8 +968,7 @@
   content::WindowedNotificationObserver nav_observer(
       content::NOTIFICATION_NAV_ENTRY_COMMITTED,
       content::NotificationService::AllSources());
-  oldtab->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(), ASCIIToUTF16(dont_fork_popup));
+  oldtab->GetMainFrame()->ExecuteJavaScript(ASCIIToUTF16(dont_fork_popup));
 
   // Wait for popup window to appear and finish navigating.
   popup_observer.Wait();
@@ -1003,8 +994,7 @@
   content::WindowedNotificationObserver nav_observer2(
         content::NOTIFICATION_NAV_ENTRY_COMMITTED,
         content::NotificationService::AllSources());
-  oldtab->GetRenderViewHost()->
-      ExecuteJavascriptInWebFrame(base::string16(), ASCIIToUTF16(navigate_str));
+  oldtab->GetMainFrame()->ExecuteJavaScript(ASCIIToUTF16(navigate_str));
   nav_observer2.Wait();
   ASSERT_TRUE(oldtab->GetController().GetLastCommittedEntry());
   EXPECT_EQ(https_url.spec(),
@@ -1810,8 +1800,7 @@
   ui_test_utils::NavigateToURL(browser(), url);
 
   WebContents* contents = browser()->tab_strip_model()->GetActiveWebContents();
-  contents->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(),
+  contents->GetMainFrame()->ExecuteJavaScript(
       ASCIIToUTF16("alert('Dialog showing!');"));
   AppModalDialog* alert = ui_test_utils::WaitForAppModalDialog();
   EXPECT_TRUE(alert->IsValid());
diff --git a/chrome/browser/ui/cocoa/applescript/tab_applescript.mm b/chrome/browser/ui/cocoa/applescript/tab_applescript.mm
index 1113e8e..8039244 100644
--- a/chrome/browser/ui/cocoa/applescript/tab_applescript.mm
+++ b/chrome/browser/ui/cocoa/applescript/tab_applescript.mm
@@ -317,8 +317,8 @@
 }
 
 - (id)handlesExecuteJavascriptScriptCommand:(NSScriptCommand*)command {
-  RenderViewHost* view = webContents_->GetRenderViewHost();
-  if (!view) {
+  content::RenderFrameHost* frame = webContents_->GetMainFrame();
+  if (!frame) {
     NOTREACHED();
     return nil;
   }
@@ -326,15 +326,12 @@
   NSAppleEventManager* manager = [NSAppleEventManager sharedAppleEventManager];
   NSAppleEventManagerSuspensionID suspensionID =
       [manager suspendCurrentAppleEvent];
-  content::RenderViewHost::JavascriptResultCallback callback =
+  content::RenderFrameHost::JavaScriptResultCallback callback =
       base::Bind(&ResumeAppleEventAndSendReply, suspensionID);
 
   base::string16 script = base::SysNSStringToUTF16(
       [[command evaluatedArguments] objectForKey:@"javascript"]);
-  view->ExecuteJavascriptInWebFrameCallbackResult(
-      base::string16(),  // frame_xpath
-      script,
-      callback);
+  frame->ExecuteJavaScript(script, callback);
 
   return nil;
 }
diff --git a/chrome/browser/ui/views/select_file_dialog_extension_browsertest.cc b/chrome/browser/ui/views/select_file_dialog_extension_browsertest.cc
index 482683d4b..2448e8b 100644
--- a/chrome/browser/ui/views/select_file_dialog_extension_browsertest.cc
+++ b/chrome/browser/ui/views/select_file_dialog_extension_browsertest.cc
@@ -25,6 +25,7 @@
 #include "chrome/common/pref_names.h"
 #include "content/public/browser/notification_service.h"
 #include "content/public/browser/notification_types.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/test/test_utils.h"
 #include "ui/shell_dialogs/select_file_dialog.h"
@@ -194,7 +195,6 @@
         content::NOTIFICATION_RENDER_WIDGET_HOST_DESTROYED,
         content::NotificationService::AllSources());
     content::RenderViewHost* host = dialog_->GetRenderViewHost();
-    base::string16 main_frame;
     std::string button_class =
         (button_type == DIALOG_BTN_OK) ? ".button-panel .ok" :
                                          ".button-panel .cancel";
@@ -203,7 +203,7 @@
         "document.querySelector(\'" + button_class + "\').click();");
     // The file selection handler closes the dialog and does not return control
     // to JavaScript, so do not wait for return values.
-    host->ExecuteJavascriptInWebFrame(main_frame, script);
+    host->GetMainFrame()->ExecuteJavaScript(script);
     LOG(INFO) << "Waiting for window close notification.";
     host_destroyed.Wait();
 
diff --git a/chrome/browser/ui/webui/memory_internals/memory_internals_handler.cc b/chrome/browser/ui/webui/memory_internals/memory_internals_handler.cc
index c666e8a..2506360 100644
--- a/chrome/browser/ui/webui/memory_internals/memory_internals_handler.cc
+++ b/chrome/browser/ui/webui/memory_internals/memory_internals_handler.cc
@@ -12,7 +12,7 @@
 #include "base/values.h"
 #include "chrome/browser/ui/webui/memory_internals/memory_internals_proxy.h"
 #include "content/public/browser/browser_thread.h"
-#include "content/public/browser/render_view_host.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/browser/web_ui.h"
 
@@ -39,9 +39,8 @@
 }
 
 void MemoryInternalsHandler::OnUpdate(const base::string16& update) {
-  // Don't try to execute JavaScript in a RenderView that no longer exists.
-  content::RenderViewHost* host =
-      web_ui()->GetWebContents()->GetRenderViewHost();
-  if (host)
-    host->ExecuteJavascriptInWebFrame(base::string16(), update);
+  // Don't try to execute JavaScript in a RenderFrame that no longer exists.
+  content::RenderFrameHost* frame = web_ui()->GetWebContents()->GetMainFrame();
+  if (frame)
+    frame->ExecuteJavaScript(update);
 }
diff --git a/chrome/browser/ui/webui/net_internals/net_internals_ui_browsertest.cc b/chrome/browser/ui/webui/net_internals/net_internals_ui_browsertest.cc
index 6c8e5b34..6f62e8d 100644
--- a/chrome/browser/ui/webui/net_internals/net_internals_ui_browsertest.cc
+++ b/chrome/browser/ui/webui/net_internals/net_internals_ui_browsertest.cc
@@ -23,7 +23,7 @@
 #include "chrome/browser/ui/webui/net_internals/net_internals_ui.h"
 #include "chrome/common/chrome_switches.h"
 #include "chrome/test/base/ui_test_utils.h"
-#include "content/public/browser/render_view_host.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/browser/web_ui_message_handler.h"
 #include "net/base/address_list.h"
@@ -278,10 +278,9 @@
     const base::ListValue* list_value) {
   std::string url;
   ASSERT_TRUE(list_value->GetString(0, &url));
-  content::RenderViewHost* host =
-      browser()->tab_strip_model()->GetWebContentsAt(1)->GetRenderViewHost();
-  host->ExecuteJavascriptInWebFrame(
-      base::string16(),
+  content::RenderFrameHost* frame =
+      browser()->tab_strip_model()->GetWebContentsAt(1)->GetMainFrame();
+  frame->ExecuteJavaScript(
       base::ASCIIToUTF16(base::StringPrintf("Click('%s')", url.c_str())));
 }
 
diff --git a/chrome/browser/ui/webui/web_ui_test_handler.cc b/chrome/browser/ui/webui/web_ui_test_handler.cc
index de7131c..8f1d7b70 100644
--- a/chrome/browser/ui/webui/web_ui_test_handler.cc
+++ b/chrome/browser/ui/webui/web_ui_test_handler.cc
@@ -13,6 +13,7 @@
 #include "content/public/browser/notification_details.h"
 #include "content/public/browser/notification_registrar.h"
 #include "content/public/browser/notification_types.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/browser/web_ui.h"
@@ -36,20 +37,17 @@
 }
 
 void WebUITestHandler::RunJavaScript(const base::string16& js_text) {
-  web_ui()->GetWebContents()->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(), js_text);
+  web_ui()->GetWebContents()->GetMainFrame()->ExecuteJavaScript(js_text);
 }
 
 bool WebUITestHandler::RunJavaScriptTestWithResult(
     const base::string16& js_text) {
   test_succeeded_ = false;
   run_test_succeeded_ = false;
-  RenderViewHost* rvh = web_ui()->GetWebContents()->GetRenderViewHost();
-  rvh->ExecuteJavascriptInWebFrameCallbackResult(
-      base::string16(),  // frame_xpath
-      js_text,
-      base::Bind(&WebUITestHandler::JavaScriptComplete,
-                 base::Unretained(this)));
+  content::RenderFrameHost* frame = web_ui()->GetWebContents()->GetMainFrame();
+  frame->ExecuteJavaScript(js_text,
+                           base::Bind(&WebUITestHandler::JavaScriptComplete,
+                                      base::Unretained(this)));
   return WaitForResult();
 }
 
diff --git a/components/dom_distiller/content/distiller_page_web_contents.cc b/components/dom_distiller/content/distiller_page_web_contents.cc
index 06bd6bc..649593cf 100644
--- a/components/dom_distiller/content/distiller_page_web_contents.cc
+++ b/components/dom_distiller/content/distiller_page_web_contents.cc
@@ -10,6 +10,7 @@
 #include "components/dom_distiller/core/distiller_page.h"
 #include "content/public/browser/browser_context.h"
 #include "content/public/browser/navigation_controller.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/browser/web_contents_observer.h"
@@ -49,14 +50,12 @@
 
 void DistillerPageWebContents::ExecuteJavaScriptImpl(
     const std::string& script) {
-  content::RenderViewHost* host = web_contents_->GetRenderViewHost();
-  DCHECK(host);
-  host->ExecuteJavascriptInWebFrameCallbackResult(
-      base::string16(),  // frame_xpath
-      base::UTF8ToUTF16(script),
-      base::Bind(&DistillerPage::OnExecuteJavaScriptDone,
-                 base::Unretained(this),
-                 web_contents_->GetLastCommittedURL()));
+  content::RenderFrameHost* frame = web_contents_->GetMainFrame();
+  DCHECK(frame);
+  frame->ExecuteJavaScript(base::UTF8ToUTF16(script),
+                           base::Bind(&DistillerPage::OnExecuteJavaScriptDone,
+                                      base::Unretained(this),
+                                      web_contents_->GetLastCommittedURL()));
 }
 
 void DistillerPageWebContents::DidFinishLoad(int64 frame_id,
diff --git a/content/browser/accessibility/accessibility_win_browsertest.cc b/content/browser/accessibility/accessibility_win_browsertest.cc
index 10e5bd6..2fd8806 100644
--- a/content/browser/accessibility/accessibility_win_browsertest.cc
+++ b/content/browser/accessibility/accessibility_win_browsertest.cc
@@ -13,7 +13,7 @@
 #include "content/browser/renderer_host/render_view_host_impl.h"
 #include "content/public/browser/notification_service.h"
 #include "content/public/browser/notification_types.h"
-#include "content/public/browser/render_view_host.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_widget_host_view.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/common/url_constants.h"
@@ -179,8 +179,7 @@
 }
 
 void AccessibilityWinBrowserTest::ExecuteScript(const std::wstring& script) {
-  shell()->web_contents()->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      std::wstring(), script);
+  shell()->web_contents()->GetMainFrame()->ExecuteJavaScript(script);
 }
 
 
diff --git a/content/browser/android/content_view_core_impl.cc b/content/browser/android/content_view_core_impl.cc
index 89eb4b7..8fc4b16 100644
--- a/content/browser/android/content_view_core_impl.cc
+++ b/content/browser/android/content_view_core_impl.cc
@@ -46,6 +46,7 @@
 #include "content/public/browser/notification_service.h"
 #include "content/public/browser/notification_source.h"
 #include "content/public/browser/notification_types.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/common/content_client.h"
 #include "content/public/common/content_switches.h"
@@ -1579,8 +1580,8 @@
 
   if (!callback) {
     // No callback requested.
-    rvh->ExecuteJavascriptInWebFrame(base::string16(),  // frame_xpath
-                                     ConvertJavaStringToUTF16(env, script));
+    web_contents_->GetMainFrame()->ExecuteJavaScript(
+        ConvertJavaStringToUTF16(env, script));
     return;
   }
 
@@ -1588,11 +1589,10 @@
   // base::Callback.
   ScopedJavaGlobalRef<jobject> j_callback;
   j_callback.Reset(env, callback);
-  content::RenderViewHost::JavascriptResultCallback c_callback =
+  content::RenderFrameHost::JavaScriptResultCallback c_callback =
       base::Bind(&JavaScriptResultCallback, j_callback);
 
-  rvh->ExecuteJavascriptInWebFrameCallbackResult(
-      base::string16(),  // frame_xpath
+  web_contents_->GetMainFrame()->ExecuteJavaScript(
       ConvertJavaStringToUTF16(env, script),
       c_callback);
 }
diff --git a/content/browser/browser_plugin/browser_plugin_guest.cc b/content/browser/browser_plugin/browser_plugin_guest.cc
index 7cd41e4..916b2dc 100644
--- a/content/browser/browser_plugin/browser_plugin_guest.cc
+++ b/content/browser/browser_plugin/browser_plugin_guest.cc
@@ -1122,8 +1122,8 @@
     const char script[] = "window.addEventListener('dragstart', function() { "
                           "  window.event.preventDefault(); "
                           "});";
-    render_view_host->ExecuteJavascriptInWebFrame(base::string16(),
-                                                  base::ASCIIToUTF16(script));
+    render_view_host->GetMainFrame()->ExecuteJavaScript(
+        base::ASCIIToUTF16(script));
   }
 }
 
diff --git a/content/browser/frame_host/render_frame_host_impl.cc b/content/browser/frame_host/render_frame_host_impl.cc
index 1805042..a70eb93 100644
--- a/content/browser/frame_host/render_frame_host_impl.cc
+++ b/content/browser/frame_host/render_frame_host_impl.cc
@@ -197,6 +197,24 @@
   Send(new FrameMsg_CSSInsertRequest(routing_id_, css));
 }
 
+void RenderFrameHostImpl::ExecuteJavaScript(
+    const base::string16& javascript) {
+  Send(new FrameMsg_JavaScriptExecuteRequest(routing_id_,
+                                             javascript,
+                                             0, false));
+}
+
+void RenderFrameHostImpl::ExecuteJavaScript(
+     const base::string16& javascript,
+     const JavaScriptResultCallback& callback) {
+  static int next_id = 1;
+  int key = next_id++;
+  Send(new FrameMsg_JavaScriptExecuteRequest(routing_id_,
+                                             javascript,
+                                             key, true));
+  javascript_callbacks_.insert(std::make_pair(key, callback));
+}
+
 RenderViewHost* RenderFrameHostImpl::GetRenderViewHost() {
   return render_view_host_;
 }
@@ -234,6 +252,8 @@
     IPC_MESSAGE_HANDLER(FrameHostMsg_BeforeUnload_ACK, OnBeforeUnloadACK)
     IPC_MESSAGE_HANDLER(FrameHostMsg_SwapOut_ACK, OnSwapOutACK)
     IPC_MESSAGE_HANDLER(FrameHostMsg_ContextMenu, OnContextMenu)
+    IPC_MESSAGE_HANDLER(FrameHostMsg_JavaScriptExecuteResponse,
+                        OnJavaScriptExecuteResponse)
   IPC_END_MESSAGE_MAP_EX()
 
   if (!msg_is_ok) {
@@ -500,6 +520,25 @@
   delegate_->ShowContextMenu(this, validated_params);
 }
 
+void RenderFrameHostImpl::OnJavaScriptExecuteResponse(
+    int id, const base::ListValue& result) {
+  const base::Value* result_value;
+  if (!result.Get(0, &result_value)) {
+    // Programming error or rogue renderer.
+    NOTREACHED() << "Got bad arguments for OnJavaScriptExecuteResponse";
+    return;
+  }
+
+  std::map<int, JavaScriptResultCallback>::iterator it =
+      javascript_callbacks_.find(id);
+  if (it != javascript_callbacks_.end()) {
+    it->second.Run(result_value);
+    javascript_callbacks_.erase(it);
+  } else {
+    NOTREACHED() << "Received script response for unknown request";
+  }
+}
+
 void RenderFrameHostImpl::SetPendingShutdown(const base::Closure& on_swap_out) {
   render_view_host_->SetPendingShutdown(on_swap_out);
 }
diff --git a/content/browser/frame_host/render_frame_host_impl.h b/content/browser/frame_host/render_frame_host_impl.h
index cb5adc7..0e2ed9bd 100644
--- a/content/browser/frame_host/render_frame_host_impl.h
+++ b/content/browser/frame_host/render_frame_host_impl.h
@@ -5,6 +5,7 @@
 #ifndef CONTENT_BROWSER_FRAME_HOST_RENDER_FRAME_HOST_IMPL_H_
 #define CONTENT_BROWSER_FRAME_HOST_RENDER_FRAME_HOST_IMPL_H_
 
+#include <map>
 #include <string>
 #include <vector>
 
@@ -23,6 +24,7 @@
 
 namespace base {
 class FilePath;
+class ListValue;
 }
 
 namespace content {
@@ -61,6 +63,11 @@
   virtual void Copy() OVERRIDE;
   virtual void Paste() OVERRIDE;
   virtual void InsertCSS(const std::string& css) OVERRIDE;
+  virtual void ExecuteJavaScript(
+      const base::string16& javascript) OVERRIDE;
+  virtual void ExecuteJavaScript(
+      const base::string16& javascript,
+      const JavaScriptResultCallback& callback) OVERRIDE;
   virtual RenderViewHost* GetRenderViewHost() OVERRIDE;
 
   // IPC::Sender
@@ -178,6 +185,7 @@
       const base::TimeTicks& renderer_before_unload_end_time);
   void OnSwapOutACK();
   void OnContextMenu(const ContextMenuParams& params);
+  void OnJavaScriptExecuteResponse(int id, const base::ListValue& result);
 
   // Returns whether the given URL is allowed to commit in the current process.
   // This is a more conservative check than RenderProcessHost::FilterURL, since
@@ -214,6 +222,10 @@
   // The FrameTreeNode which this RenderFrameHostImpl is hosted in.
   FrameTreeNode* frame_tree_node_;
 
+  // The mapping of pending JavaScript calls created by
+  // ExecuteJavaScript and their corresponding callbacks.
+  std::map<int, JavaScriptResultCallback> javascript_callbacks_;
+
   int routing_id_;
   bool is_swapped_out_;
 
diff --git a/content/browser/media/media_internals_handler.cc b/content/browser/media/media_internals_handler.cc
index 9a3e7be..74eb8354 100644
--- a/content/browser/media/media_internals_handler.cc
+++ b/content/browser/media/media_internals_handler.cc
@@ -9,7 +9,7 @@
 #include "base/values.h"
 #include "content/browser/media/media_internals_proxy.h"
 #include "content/public/browser/browser_thread.h"
-#include "content/public/browser/render_view_host.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/browser/web_ui.h"
 
@@ -41,9 +41,9 @@
 void MediaInternalsMessageHandler::OnUpdate(const base::string16& update) {
   // Don't try to execute JavaScript in a RenderView that no longer exists nor
   // if the chrome://media-internals page hasn't finished loading.
-  RenderViewHost* host = web_ui()->GetWebContents()->GetRenderViewHost();
+  RenderFrameHost* host = web_ui()->GetWebContents()->GetMainFrame();
   if (host && page_load_complete_)
-    host->ExecuteJavascriptInWebFrame(base::string16(), update);
+    host->ExecuteJavaScript(update);
 }
 
 }  // namespace content
diff --git a/content/browser/media/webrtc_internals_message_handler.cc b/content/browser/media/webrtc_internals_message_handler.cc
index be1722c..7a31bb4 100644
--- a/content/browser/media/webrtc_internals_message_handler.cc
+++ b/content/browser/media/webrtc_internals_message_handler.cc
@@ -7,8 +7,8 @@
 #include "content/browser/media/webrtc_internals.h"
 #include "content/common/media/peer_connection_tracker_messages.h"
 #include "content/public/browser/browser_thread.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_process_host.h"
-#include "content/public/browser/render_view_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/browser/web_ui.h"
 
@@ -65,9 +65,9 @@
     std::vector<const base::Value*> args_vector;
     base::string16 script = WebUI::GetJavascriptCall("setAecRecordingEnabled",
                                                      args_vector);
-    RenderViewHost* host = web_ui()->GetWebContents()->GetRenderViewHost();
+    RenderFrameHost* host = web_ui()->GetWebContents()->GetMainFrame();
     if (host)
-      host->ExecuteJavascriptInWebFrame(base::string16(), script);
+      host->ExecuteJavaScript(script);
   }
 }
 
@@ -78,9 +78,9 @@
   args_vector.push_back(args);
   base::string16 update = WebUI::GetJavascriptCall(command, args_vector);
 
-  RenderViewHost* host = web_ui()->GetWebContents()->GetRenderViewHost();
+  RenderFrameHost* host = web_ui()->GetWebContents()->GetMainFrame();
   if (host)
-    host->ExecuteJavascriptInWebFrame(base::string16(), update);
+    host->ExecuteJavaScript(update);
 }
 
 }  // namespace content
diff --git a/content/common/frame_messages.h b/content/common/frame_messages.h
index d4aa7a0..25c760b 100644
--- a/content/common/frame_messages.h
+++ b/content/common/frame_messages.h
@@ -304,6 +304,20 @@
 IPC_MESSAGE_ROUTED1(FrameMsg_CSSInsertRequest,
                     std::string  /* css */)
 
+// Request for the renderer to execute JavaScript in the frame's context.
+//
+// javascript is the string containing the JavaScript to be executed in the
+// target frame's context.
+//
+// If the third parameter is true the result is sent back to the browser using
+// the message FrameHostMsg_JavaScriptExecuteResponse.
+// FrameHostMsg_JavaScriptExecuteResponse is passed the ID parameter so that the
+// host can uniquely identify the request.
+IPC_MESSAGE_ROUTED3(FrameMsg_JavaScriptExecuteRequest,
+                    base::string16,  /* javascript */
+                    int,  /* ID */
+                    bool  /* if true, a reply is requested */)
+
 // -----------------------------------------------------------------------------
 // Messages sent from the renderer to the browser.
 
@@ -468,3 +482,12 @@
 IPC_MESSAGE_ROUTED2(FrameHostMsg_InitializeChildFrame,
                     gfx::Rect /* frame_rect */,
                     float /* scale_factor */)
+
+// Response for FrameMsg_JavaScriptExecuteRequest, sent when a reply was
+// requested. The ID is the parameter supplied to
+// FrameMsg_JavaScriptExecuteRequest. The result has the value returned by the
+// script as its only element, one of Null, Boolean, Integer, Real, Date, or
+// String.
+IPC_MESSAGE_ROUTED2(FrameHostMsg_JavaScriptExecuteResponse,
+                    int  /* id */,
+                    base::ListValue  /* result */)
diff --git a/content/public/browser/render_frame_host.h b/content/public/browser/render_frame_host.h
index dd540ba..c044d830 100644
--- a/content/public/browser/render_frame_host.h
+++ b/content/public/browser/render_frame_host.h
@@ -5,12 +5,17 @@
 #ifndef CONTENT_PUBLIC_BROWSER_RENDER_FRAME_HOST_H_
 #define CONTENT_PUBLIC_BROWSER_RENDER_FRAME_HOST_H_
 
+#include "base/callback_forward.h"
 #include "content/common/content_export.h"
 #include "ipc/ipc_listener.h"
 #include "ipc/ipc_sender.h"
 #include "ui/gfx/native_widget_types.h"
 #include "url/gurl.h"
 
+namespace base {
+class Value;
+}
+
 namespace content {
 class RenderProcessHost;
 class RenderViewHost;
@@ -84,6 +89,13 @@
   // Requests the renderer to insert CSS into the frame's document.
   virtual void InsertCSS(const std::string& css) = 0;
 
+  // Runs some JavaScript in this frame's context. If a callback is provided, it
+  // will be used to return the result, when the result is available.
+  typedef base::Callback<void(const base::Value*)> JavaScriptResultCallback;
+  virtual void ExecuteJavaScript(const base::string16& javascript) = 0;
+  virtual void ExecuteJavaScript(const base::string16& javascript,
+                                 const JavaScriptResultCallback& callback) = 0;
+
   // Temporary until we get rid of RenderViewHost.
   virtual RenderViewHost* GetRenderViewHost() = 0;
 
diff --git a/content/public/browser/render_view_host.h b/content/public/browser/render_view_host.h
index d1549ad..1487130 100644
--- a/content/public/browser/render_view_host.h
+++ b/content/public/browser/render_view_host.h
@@ -159,11 +159,13 @@
       const blink::WebMediaPlayerAction& action) = 0;
 
   // Runs some javascript within the context of a frame in the page.
+  // OBSOLETE; DO NOT USE! Use RenderFrameHost::ExecuteJavaScript instead.
   virtual void ExecuteJavascriptInWebFrame(const base::string16& frame_xpath,
                                            const base::string16& jscript) = 0;
 
   // Runs some javascript within the context of a frame in the page. The result
   // is sent back via the provided callback.
+  // OBSOLETE; DO NOT USE! Use RenderFrameHost::ExecuteJavaScript instead.
   typedef base::Callback<void(const base::Value*)> JavascriptResultCallback;
   virtual void ExecuteJavascriptInWebFrameCallbackResult(
       const base::string16& frame_xpath,
diff --git a/content/renderer/render_frame_impl.cc b/content/renderer/render_frame_impl.cc
index 2cbc751..37654f8 100644
--- a/content/renderer/render_frame_impl.cc
+++ b/content/renderer/render_frame_impl.cc
@@ -56,6 +56,7 @@
 #include "content/renderer/render_widget_fullscreen_pepper.h"
 #include "content/renderer/renderer_webapplicationcachehost_impl.h"
 #include "content/renderer/shared_worker_repository.h"
+#include "content/renderer/v8_value_converter_impl.h"
 #include "content/renderer/websharedworker_proxy.h"
 #include "net/base/data_url.h"
 #include "net/base/net_errors.h"
@@ -73,6 +74,7 @@
 #include "third_party/WebKit/public/web/WebNavigationPolicy.h"
 #include "third_party/WebKit/public/web/WebPlugin.h"
 #include "third_party/WebKit/public/web/WebPluginParams.h"
+#include "third_party/WebKit/public/web/WebScriptSource.h"
 #include "third_party/WebKit/public/web/WebSearchableFormData.h"
 #include "third_party/WebKit/public/web/WebSecurityOrigin.h"
 #include "third_party/WebKit/public/web/WebSecurityPolicy.h"
@@ -105,6 +107,7 @@
 using blink::WebNode;
 using blink::WebPluginParams;
 using blink::WebReferrerPolicy;
+using blink::WebScriptSource;
 using blink::WebSearchableFormData;
 using blink::WebSecurityOrigin;
 using blink::WebSecurityPolicy;
@@ -549,6 +552,8 @@
     IPC_MESSAGE_HANDLER(InputMsg_Copy, OnCopy)
     IPC_MESSAGE_HANDLER(InputMsg_Paste, OnPaste)
     IPC_MESSAGE_HANDLER(FrameMsg_CSSInsertRequest, OnCSSInsertRequest)
+    IPC_MESSAGE_HANDLER(FrameMsg_JavaScriptExecuteRequest,
+                        OnJavaScriptExecuteRequest)
   IPC_END_MESSAGE_MAP_EX()
 
   if (!msg_is_ok) {
@@ -885,6 +890,33 @@
   frame_->document().insertStyleSheet(WebString::fromUTF8(css));
 }
 
+void RenderFrameImpl::OnJavaScriptExecuteRequest(
+    const base::string16& jscript,
+    int id,
+    bool notify_result) {
+  TRACE_EVENT_INSTANT0("test_tracing", "OnJavaScriptExecuteRequest",
+                       TRACE_EVENT_SCOPE_THREAD);
+
+  v8::HandleScope handle_scope(v8::Isolate::GetCurrent());
+  v8::Handle<v8::Value> result =
+      frame_->executeScriptAndReturnValue(WebScriptSource(jscript));
+  if (notify_result) {
+    base::ListValue list;
+    if (!result.IsEmpty()) {
+      v8::Local<v8::Context> context = frame_->mainWorldScriptContext();
+      v8::Context::Scope context_scope(context);
+      V8ValueConverterImpl converter;
+      converter.SetDateAllowed(true);
+      converter.SetRegExpAllowed(true);
+      base::Value* result_value = converter.FromV8Value(result, context);
+      list.Set(0, result_value ? result_value : base::Value::CreateNullValue());
+    } else {
+      list.Set(0, base::Value::CreateNullValue());
+    }
+    Send(new FrameHostMsg_JavaScriptExecuteResponse(routing_id_, id, list));
+  }
+}
+
 bool RenderFrameImpl::ShouldUpdateSelectionTextFromContextMenuParams(
     const base::string16& selection_text,
     size_t selection_text_offset,
diff --git a/content/renderer/render_frame_impl.h b/content/renderer/render_frame_impl.h
index 1004340a..230821c 100644
--- a/content/renderer/render_frame_impl.h
+++ b/content/renderer/render_frame_impl.h
@@ -373,6 +373,9 @@
   void OnCopy();
   void OnPaste();
   void OnCSSInsertRequest(const std::string& css);
+  void OnJavaScriptExecuteRequest(const base::string16& javascript,
+                                  int id,
+                                  bool notify_result);
 
   // Virtual since overridden by WebTestProxy for layout tests.
   virtual blink::WebNavigationPolicy DecidePolicyForNavigation(
diff --git a/content/shell/browser/shell_devtools_frontend.cc b/content/shell/browser/shell_devtools_frontend.cc
index fa3d16d..93f1a3a 100644
--- a/content/shell/browser/shell_devtools_frontend.cc
+++ b/content/shell/browser/shell_devtools_frontend.cc
@@ -10,6 +10,7 @@
 #include "base/strings/utf_string_conversions.h"
 #include "content/public/browser/devtools_http_handler.h"
 #include "content/public/browser/devtools_manager.h"
+#include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_view_host.h"
 #include "content/public/browser/web_contents.h"
 #include "content/public/browser/web_contents_view.h"
@@ -118,8 +119,7 @@
 }
 
 void ShellDevToolsFrontend::DocumentOnLoadCompletedInMainFrame(int32 page_id) {
-  web_contents()->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
-      base::string16(),
+  web_contents()->GetMainFrame()->ExecuteJavaScript(
       base::ASCIIToUTF16("InspectorFrontendAPI.setUseSoftMenu(true);"));
 }