Give the main frame a RenderWidget.

Currently, RenderView is a subclass of RenderWidget, and the RenderWidget
portion is effectively treated as the  the widget for the main frame as
well. For a number of reasons, this is a problematic model:

- A remote frame doesn't need a widget; however, a RenderView with a remote
  main frame still has a vestigal RenderWidget.
- Code that needs to affect both RenderWidget / RenderView is awkwardly
  split between them, in both content and blink.
- RenderView itself is often seen as an easy entry point to perform
  page-level work in the renderer. With OOPI, this is no longer a valid
  assumption.

In order to incrementally de-widgetize RenderView, the main frame will
have also have a RenderWidget, to make it consistent with the local frame
roots for subframes, which already have a RenderWidget. However, instead of
giving main frames their own RenderWidget, the main frame re-uses the
RenderView as its RenderWidget.

The rationale for taking this approach is to minimize the breakage: today,
Chrome simply doesn't expect to have two "widgets" for a frame.
Instantiating a distinct RenderWidget for the main frame can confuse code
that iterates or counts the active widgets: an example of this is the
security check for injecting WebUI bindings.

In the future, when RenderViewHost has-a RenderWidgetHost (and similarly,
when RenderViewImpl has-a RenderWidget) instead of today's is-a relation,
then it be conceptually much more straightforward to transition completely
to the new model.

BUG=419087

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

Cr-Commit-Position: refs/heads/master@{#356176}
diff --git a/content/renderer/render_widget.cc b/content/renderer/render_widget.cc
index 2ece707..44b971f 100644
--- a/content/renderer/render_widget.cc
+++ b/content/renderer/render_widget.cc
@@ -50,6 +50,7 @@
 #include "content/renderer/render_frame_proxy.h"
 #include "content/renderer/render_process.h"
 #include "content/renderer/render_thread_impl.h"
+#include "content/renderer/render_view_impl.h"
 #include "content/renderer/renderer_blink_platform_impl.h"
 #include "content/renderer/resizing_mode_selector.h"
 #include "ipc/ipc_sync_message.h"
@@ -571,6 +572,14 @@
     CompositorDependencies* compositor_deps,
     blink::WebLocalFrame* frame) {
   CHECK_NE(routing_id, MSG_ROUTING_NONE);
+  // TODO(avi): Before RenderViewImpl has-a RenderWidget, the browser passes the
+  // same routing ID for both the view routing ID and the main frame widget
+  // routing ID. https://crbug.com/545684
+  RenderViewImpl* view = RenderViewImpl::FromRoutingID(routing_id);
+  if (view) {
+    view->AttachWebFrameWidget(RenderWidget::CreateWebFrameWidget(view, frame));
+    return view;
+  }
   scoped_refptr<RenderWidget> widget(
       new RenderWidget(compositor_deps, blink::WebPopupTypeNone, screen_info,
                        false, hidden, false));
@@ -590,6 +599,11 @@
 blink::WebWidget* RenderWidget::CreateWebFrameWidget(
     RenderWidget* render_widget,
     blink::WebLocalFrame* frame) {
+  if (!frame->parent()) {
+    // TODO(dcheng): The main frame widget currently has a special case.
+    // Eliminate this once WebView is no longer a WebWidget.
+    return blink::WebFrameWidget::create(render_widget, frame->view(), frame);
+  }
   return blink::WebFrameWidget::create(render_widget, frame);
 }