New issue
Advanced search Search tips

Issue 657007 link

Starred by 2 users

Issue metadata

Status: Assigned
Owner:
Components:
EstimatedDays: ----
NextAction: ----
OS: Android
Pri: 3
Type: Bug



Sign in to add a comment

Tabs being reparented must stay associated with old activity, or cause crashes

Project Member Reported by mthiesse@chromium.org, Oct 18 2016

Issue description

Currently navigation, and many other things, require the Tab to be associated with an Activity, so we can't set the WindowAndroid for the Tab to null while re-parenting.

See crbug.com/648865 for example of when navigation can be triggered during reparenting.

Some locations that expect the Tab to always be associated with an Activity (this list is probably not exhaustive):
InterceptNavigationDelegateImpl#shouldIgnoreNavigation
InterceptNavigationDelegateImpl#onOverrideUrlLoadingAndLaunchIntent
TabContextMenuItemDelegate#onOpenImageInNewTab
TabContextMenuItemDelegate#onOpenInChrome
TabContextMenuItemDelegate#onOpenInOtherWindow
TabWebContentsDelegateAndroid#activateContents
TabWebContentsDelegateAndroid#addNewContents
TabWebContentsDelegateAndroid#getContentVideoViewEmbedder
TabWebContentsDelegateAndroid#handleKeyboardEvent
TabWebContentsDelegateAndroid#closeContents
TabWebContentsDelegateAndroid#shouldResumeRequestsForCreatedWindow
TabWebContentsDelegateAndroid#webContentsCreated
Tab#setPendingPrint
NewTabPage#destroy  (getSnackbarManager())
NewTabPage#showMostVisitedItemRemovedSnackbar  (getSnackbarManager())
InterceptNavigationDelegateImpl#onOverrideUrlLoadingAndLaunchIntent  (getTabModelSelector())
TabContextMenuItemDelegate#onOpenInNewIncognitoTab  (getTabModelSelector())
TabContextMenuItemDelegate#onOpenInNewTab  (getTabModelSelector())
TabWebContentsDelegateAndroid#closeContents  (getTabModelSelector())
TabWebContentsDelegateAndroid#getTabModel  (getTabModelSelector())

Some locations that expect the tab to always be associated with a WindowAndroid:
GoogleAuthenticatorNavigationInterceptor#GoogleAuthenticatorNavigationInterceptor
ChromeApplication#openClearBrowsingData
ContextualSearchTabHelper#getContextualSearchManager
ChromeDownloadDelegate#closeBlankTab
ChromeDownloadDelegate#requestFileAccess
ChromeDownloadDelegate#shouldInterceptContextMenuDownload
ExternalNavigationDelegateImpl#closeTab
ExternalNavigationDelegateImpl#ExternalNavigationDelegateImpl
ExternalNavigationDelegateImpl#shouldRequestFileAccess
ExternalNavigationDelegateImpl#startFileIntent
ExternalNavigationDelegateImpl#startIncognitoIntent
AppBannerInfoBarDelegateAndroid#installOrOpenNativeApp
AppBannerInfoBarDelegateAndroid#showAppDetails
SimpleConfirmInfoBarBuilder#create
LocationBarLayout#onClick
AutoSigninSnackbarController#showSnackbar
Tab#swapWebContents
Tab#renderProcessGone
CustomTabToolbar#onNativeLibraryReady
FindResultBar#dismiss
FindResultBar#FindResultBar
 
Do you think it would be possible to make tab reparenting a synchronous operation? It would probably be easier than fixing all of the callsites.

Currently we detach the Tab, fire an Intent, and reattach when the Intent is processed.

What if we fired an intent to start the new activity (if necessary), then the target activity synchronously took ownership of the tab?

Comment 2 by yus...@chromium.org, Oct 18 2016

It is hard to "not do anything" before we launch the new Activity, mostly because when you launch a new one there are no guarantees as to what will happen to the old one (this is actually the root of some of the troubles), and when an Activity gets destroyed, it by design takes everything it owns down with it :). TabModelSelector, TabModels and Tabs all get cleared out and destroyed with all the associated renderers etc. That is why we remove the tab from the model before launching the intent.

We have to severe the renderers connection to the window, because if not it will react to window state changes and when the old activity goes away, will hide the contents, which we don't want, because it looks awful and flickering.

So before we launch the intent, we have to do "something". I agree that it is a bit weird to be able to say, we severe all ties, but leave the WindowAndroid and Activity association intact. Nevertheless, note that we actually don't finish that activity until reparenting is completely done in attachAndFinishReparenting, so relying on that old activity is technically OK. But the uncertainties about Activities dying on their own again come back to bite us here.

All in all, it would probably be hard to make everything synchronous, but I agree we can make some more of these synchronous.

Sign in to add a comment