Browse Source

fix: ensure history navigations are sandboxed-iframe-aware (#35420)

Jeremy Spiegel 2 years ago
parent
commit
730d9181b3

+ 0 - 5
shell/browser/api/electron_api_web_contents.cc

@@ -1380,11 +1380,6 @@ bool WebContents::HandleContextMenu(content::RenderFrameHost& render_frame_host,
   return true;
 }
 
-bool WebContents::OnGoToEntryOffset(int offset) {
-  GoToOffset(offset);
-  return false;
-}
-
 void WebContents::FindReply(content::WebContents* web_contents,
                             int request_id,
                             int number_of_matches,

+ 0 - 1
shell/browser/api/electron_api_web_contents.h

@@ -534,7 +534,6 @@ class WebContents : public ExclusiveAccessContext,
       content::RenderWidgetHost* render_widget_host) override;
   bool HandleContextMenu(content::RenderFrameHost& render_frame_host,
                          const content::ContextMenuParams& params) override;
-  bool OnGoToEntryOffset(int offset) override;
   void FindReply(content::WebContents* web_contents,
                  int request_id,
                  int number_of_matches,

+ 28 - 0
spec/chromium-spec.ts

@@ -1812,6 +1812,34 @@ describe('chromium features', () => {
         expect((w.webContents as any).length()).to.equal(2);
       });
     });
+
+    describe('window.history.back', () => {
+      it('should not allow sandboxed iframe to modify main frame state', async () => {
+        const w = new BrowserWindow({ show: false });
+        w.loadURL('data:text/html,<iframe sandbox="allow-scripts"></iframe>');
+        await Promise.all([
+          emittedOnce(w.webContents, 'navigation-entry-committed'),
+          emittedOnce(w.webContents, 'did-frame-navigate'),
+          emittedOnce(w.webContents, 'did-navigate')
+        ]);
+
+        w.webContents.executeJavaScript('window.history.pushState(1, "")');
+        await Promise.all([
+          emittedOnce(w.webContents, 'navigation-entry-committed'),
+          emittedOnce(w.webContents, 'did-navigate-in-page')
+        ]);
+
+        (w.webContents as any).once('navigation-entry-committed', () => {
+          expect.fail('Unexpected navigation-entry-committed');
+        });
+        w.webContents.once('did-navigate-in-page', () => {
+          expect.fail('Unexpected did-navigate-in-page');
+        });
+        await w.webContents.mainFrame.frames[0].executeJavaScript('window.history.back()');
+        expect(await w.webContents.executeJavaScript('window.history.state')).to.equal(1);
+        expect((w.webContents as any).getActiveIndex()).to.equal(1);
+      });
+    });
   });
 
   describe('chrome://media-internals', () => {