Merge backout of changeset 0ddf975663a0 (Bug 540692: Blocklist vksaver.dll) to test the theory that it is the cause of number 1 topcrash bug 545195.
authorL. David Baron <dbaron@dbaron.org>
Wed, 10 Feb 2010 21:53:20 -0800
changeset 38049 096332cd6d39c81d43c4df054dd70d5204a0cab6
parent 38047 bdb83d642185a8134c7e36f91d4b7c02eb49f739 (diff)
parent 38048 83adba23046790d0de32384c4c12cf5974cb839e (current diff)
child 38050 ed708256f554f30860e329148001dfc12dda3a75
push id11589
push userdbaron@mozilla.com
push dateThu, 11 Feb 2010 05:54:10 +0000
treeherdermozilla-central@096332cd6d39 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
bugs540692, 545195
milestone1.9.3a2pre
Merge backout of changeset 0ddf975663a0 (Bug 540692: Blocklist vksaver.dll) to test the theory that it is the cause of number 1 topcrash bug 545195.
--- a/accessible/src/base/nsAccessibilityAtomList.h
+++ b/accessible/src/base/nsAccessibilityAtomList.h
@@ -257,16 +257,18 @@ ACCESSIBILITY_ATOM(aria_valuenow, "aria-
 ACCESSIBILITY_ATOM(aria_valuemin, "aria-valuemin")
 ACCESSIBILITY_ATOM(aria_valuemax, "aria-valuemax")
 ACCESSIBILITY_ATOM(aria_valuetext, "aria-valuetext")
 
   // misc atoms
 // a form property used to obtain the default label
 // of an HTML button from the button frame
 ACCESSIBILITY_ATOM(defaultLabel, "defaultLabel")
+// the attribute specifying the editor's bogus br node
+ACCESSIBILITY_ATOM(mozeditorbogusnode, "_moz_editor_bogus_node")
 
 // Object attributes
 ACCESSIBILITY_ATOM(tableCellIndex, "table-cell-index")
 ACCESSIBILITY_ATOM(containerAtomic, "container-atomic")
 ACCESSIBILITY_ATOM(containerBusy, "container-busy")
 ACCESSIBILITY_ATOM(containerLive, "container-live")
 ACCESSIBILITY_ATOM(containerLiveRole, "container-live-role")
 ACCESSIBILITY_ATOM(containerRelevant, "container-relevant")
--- a/accessible/src/base/nsAccessible.cpp
+++ b/accessible/src/base/nsAccessible.cpp
@@ -3007,30 +3007,31 @@ nsAccessible::CacheChildren()
 
     walker.GetNextSibling();
   }
 }
 
 void
 nsAccessible::TestChildCache(nsAccessible *aCachedChild)
 {
-#ifdef DEBUG_A11Y
+#ifdef DEBUG
   // All cached accessible nodes should be in the parent
   // It will assert if not all the children were created
   // when they were first cached, and no invalidation
   // ever corrected parent accessible's child cache.
   PRUint32 childCount = mChildren.Length();
   if (childCount == 0) {
     NS_ASSERTION(mAreChildrenInitialized,
-                 "Children are stored but not initailzied!");
+                 "Children are stored but not initialized!");
     return;
   }
 
+  nsAccessible *child;
   for (PRInt32 childIdx = 0; childIdx < childCount; childIdx++) {
-    nsAccessible *child = GetChildAt(childIdx);
+    child = GetChildAt(childIdx);
     if (child == aCachedChild)
       break;
   }
 
   NS_ASSERTION(child == aCachedChild,
                "[TestChildCache] cached accessible wasn't found. Wrong accessible tree!");  
 #endif
 }
--- a/accessible/src/base/nsAccessible.h
+++ b/accessible/src/base/nsAccessible.h
@@ -296,32 +296,32 @@ public:
    *
    * @param aText         returned text of the accessible
    * @param aStartOffset  start offset inside of the accesible
    * @param aLength       required lenght of text
    */
   virtual nsresult AppendTextTo(nsAString& aText, PRUint32 aStartOffset,
                                 PRUint32 aLength);
 
+  /**
+   * Assert if child not in parent's cache.
+   */
+  void TestChildCache(nsAccessible *aCachedChild);
+
 protected:
 
   //////////////////////////////////////////////////////////////////////////////
   // Initializing, cache and tree traverse methods
 
   /**
    * Cache accessible children.
    */
   virtual void CacheChildren();
 
   /**
-   * Assert if child not in parent's cache.
-   */
-  void TestChildCache(nsAccessible *aCachedChild);
-
-  /**
    * Cache children if necessary. Return true if the accessible is defunct.
    */
   PRBool EnsureChildren();
 
   /**
    * Return sibling accessible at the given offset.
    */
   virtual nsIAccessible* GetSiblingAtOffset(PRInt32 aOffset,
--- a/accessible/src/base/nsDocAccessible.cpp
+++ b/accessible/src/base/nsDocAccessible.cpp
@@ -537,17 +537,17 @@ NS_IMETHODIMP nsDocAccessible::GetAssoci
     NS_ADDREF(*aEditor = editor);
   }
   return NS_OK;
 }
 
 NS_IMETHODIMP nsDocAccessible::GetCachedAccessNode(void *aUniqueID, nsIAccessNode **aAccessNode)
 {
   GetCacheEntry(mAccessNodeCache, aUniqueID, aAccessNode); // Addrefs for us
-#ifdef DEBUG_A11Y
+#ifdef DEBUG
   // All cached accessible nodes should be in the parent
   // It will assert if not all the children were created
   // when they were first cached, and no invalidation
   // ever corrected parent accessible's child cache.
   nsRefPtr<nsAccessible> acc =
     nsAccUtils::QueryObject<nsAccessible>(*aAccessNode);
 
   if (acc) {
@@ -1951,21 +1951,21 @@ nsDocAccessible::InvalidateCacheSubtree(
   childNode->GetLocalName(localName);
   const char *hasAccessible = childAccessible ? " (acc)" : "";
   if (aChangeType == nsIAccessibilityService::FRAME_HIDE)
     printf("[Hide %s %s]\n", NS_ConvertUTF16toUTF8(localName).get(), hasAccessible);
   else if (aChangeType == nsIAccessibilityService::FRAME_SHOW)
     printf("[Show %s %s]\n", NS_ConvertUTF16toUTF8(localName).get(), hasAccessible);
   else if (aChangeType == nsIAccessibilityService::FRAME_SIGNIFICANT_CHANGE)
     printf("[Layout change %s %s]\n", NS_ConvertUTF16toUTF8(localName).get(), hasAccessible);
-  else if (aChangeType == nsIAccessibleEvent::NODE_APPEND)
+  else if (aChangeType == nsIAccessibilityService::NODE_APPEND)
     printf("[Create %s %s]\n", NS_ConvertUTF16toUTF8(localName).get(), hasAccessible);
   else if (aChangeType == nsIAccessibilityService::NODE_REMOVE)
     printf("[Destroy  %s %s]\n", NS_ConvertUTF16toUTF8(localName).get(), hasAccessible);
-  else if (aChangeEventType == nsIAccessibilityService::NODE_SIGNIFICANT_CHANGE)
+  else if (aChangeType == nsIAccessibilityService::NODE_SIGNIFICANT_CHANGE)
     printf("[Type change %s %s]\n", NS_ConvertUTF16toUTF8(localName).get(), hasAccessible);
 #endif
 
   nsCOMPtr<nsIAccessible> containerAccessible;
   GetAccessibleInParentChain(childNode, PR_TRUE, getter_AddRefs(containerAccessible));
   if (!containerAccessible) {
     containerAccessible = this;
   }
--- a/accessible/src/html/nsHyperTextAccessible.cpp
+++ b/accessible/src/html/nsHyperTextAccessible.cpp
@@ -581,26 +581,24 @@ nsresult nsHyperTextAccessible::DOMPoint
   }
 
   // Get accessible for this findNode, or if that node isn't accessible, use the
   // accessible for the next DOM node which has one (based on forward depth first search)
   nsCOMPtr<nsIAccessible> descendantAccessible;
   if (findNode) {
     nsCOMPtr<nsIContent> findContent = do_QueryInterface(findNode);
     if (findContent->IsHTML() && 
-        findContent->NodeInfo()->Equals(nsAccessibilityAtoms::br)) {
-      nsIContent *parent = findContent->GetParent();
-      if (parent &&
-          parent->IsRootOfNativeAnonymousSubtree() &&
-          parent->GetChildCount() == 1) {
-        // This <br> is the only node in a text control, therefore it is the hacky
-        // "bogus node" used when there is no text in a control
-        *aHyperTextOffset = 0;
-        return NS_OK;
-      }
+        findContent->NodeInfo()->Equals(nsAccessibilityAtoms::br) &&
+        findContent->AttrValueIs(kNameSpaceID_None,
+                                 nsAccessibilityAtoms::mozeditorbogusnode,
+                                 nsAccessibilityAtoms::_true,
+                                 eIgnoreCase)) {
+      // This <br> is the hacky "bogus node" used when there is no text in a control
+      *aHyperTextOffset = 0;
+      return NS_OK;
     }
     descendantAccessible = GetFirstAvailableAccessible(findNode);
   }
   // From the descendant, go up and get the immediate child of this hypertext
   nsCOMPtr<nsIAccessible> childAccessible;
   while (descendantAccessible) {
     nsCOMPtr<nsIAccessible> parentAccessible;
     descendantAccessible->GetParent(getter_AddRefs(parentAccessible));
--- a/accessible/src/xul/nsXULMenuAccessible.cpp
+++ b/accessible/src/xul/nsXULMenuAccessible.cpp
@@ -174,26 +174,21 @@ NS_IMETHODIMP nsXULSelectableAccessible:
   nsCOMPtr<nsIDOMXULMultiSelectControlElement> xulMultiSelect =
     do_QueryInterface(mSelectControl);
   if (xulMultiSelect)
     xulMultiSelect->GetSelectedItem(aIndex, getter_AddRefs(selectedItem));
 
   if (aIndex == 0)
     mSelectControl->GetSelectedItem(getter_AddRefs(selectedItem));
 
-  if (selectedItem) {
+  if (selectedItem)
     GetAccService()->GetAccessibleInWeakShell(selectedItem, mWeakShell,
                                               aAccessible);
-    if (*aAccessible) {
-      NS_ADDREF(*aAccessible);
-      return NS_OK;
-    }
-  }
 
-  return NS_ERROR_FAILURE;
+  return (*aAccessible) ? NS_OK : NS_ERROR_FAILURE;
 }
 
 NS_IMETHODIMP nsXULSelectableAccessible::GetSelectionCount(PRInt32 *aSelectionCount)
 {
   *aSelectionCount = 0;
   if (!mSelectControl) {
     return NS_ERROR_FAILURE;
   }
--- a/browser/base/content/browser-fullZoom.js
+++ b/browser/base/content/browser-fullZoom.js
@@ -328,23 +328,23 @@ var FullZoom = {
    * and perhaps the same is true for full zoom
    * (although DocumentViewerImpl::SetFullZoom doesn't mention it).
    *
    * So when we apply new zoom values to the browser, we simply set the zoom.
    * We don't check first to see if the new value is the same as the current
    * one.
    **/
   _applyPrefToSetting: function FullZoom__applyPrefToSetting(aValue, aBrowser) {
-    if (!this.siteSpecific && !this._inPrivateBrowsing)
+    if ((!this.siteSpecific && !this._inPrivateBrowsing) ||
+        gInPrintPreviewMode)
       return;
 
     var browser = aBrowser || gBrowser.selectedBrowser;
     try {
-      if (gInPrintPreviewMode ||
-          browser.contentDocument instanceof Ci.nsIImageDocument ||
+      if (browser.contentDocument instanceof Ci.nsIImageDocument ||
           this._inPrivateBrowsing)
         ZoomManager.setZoomForBrowser(browser, 1);
       else if (typeof aValue != "undefined")
         ZoomManager.setZoomForBrowser(browser, this._ensureValid(aValue));
       else if (typeof this.globalValue != "undefined")
         ZoomManager.setZoomForBrowser(browser, this.globalValue);
       else
         ZoomManager.setZoomForBrowser(browser, 1);
--- a/browser/base/content/browser-tabPreviews.js
+++ b/browser/base/content/browser-tabPreviews.js
@@ -571,17 +571,17 @@ var allTabs = {
   },
   get previews () this.container.getElementsByClassName("allTabs-preview"),
   get isOpen () this.panel.state == "open" || this.panel.state == "showing",
 
   init: function allTabs_init() {
     if (this._initiated)
       return;
     this._initiated = true;
-	
+
     Array.forEach(gBrowser.mTabs, function (tab) {
       this._addPreview(tab);
     }, this);
 
     gBrowser.tabContainer.addEventListener("TabOpen", this, false);
     gBrowser.tabContainer.addEventListener("TabAttrModified", this, false);
     gBrowser.tabContainer.addEventListener("TabMove", this, false);
     gBrowser.tabContainer.addEventListener("TabClose", this, false);
--- a/browser/base/content/browser.js
+++ b/browser/base/content/browser.js
@@ -1096,24 +1096,28 @@ function HandleAppCommandEvent(evt) {
     BrowserHome();
     break;
   default:
     break;
   }
 }
 
 function prepareForStartup() {
+  var os = Components.classes["@mozilla.org/observer-service;1"].getService(Components.interfaces.nsIObserverService);
+
   gBrowser.addEventListener("DOMUpdatePageReport", gPopupBlockerObserver.onUpdatePageReport, false);
   // Note: we need to listen to untrusted events, because the pluginfinder XBL
   // binding can't fire trusted ones (runs with page privileges).
   gBrowser.addEventListener("PluginNotFound", gMissingPluginInstaller.newMissingPlugin, true, true);
+  gBrowser.addEventListener("PluginCrashed", gMissingPluginInstaller.pluginInstanceCrashed, true, true);
   gBrowser.addEventListener("PluginBlocklisted", gMissingPluginInstaller.newMissingPlugin, true, true);
   gBrowser.addEventListener("PluginOutdated", gMissingPluginInstaller.newMissingPlugin, true, true);
   gBrowser.addEventListener("PluginDisabled", gMissingPluginInstaller.newDisabledPlugin, true, true);
   gBrowser.addEventListener("NewPluginInstalled", gMissingPluginInstaller.refreshBrowser, false);
+  os.addObserver(gMissingPluginInstaller.pluginCrashed, "plugin-crashed", false);
   window.addEventListener("AppCommand", HandleAppCommandEvent, true);
 
   var webNavigation;
   try {
     webNavigation = getWebNavigation();
     if (!webNavigation)
       throw "no XBL binding for browser";
   } catch (e) {
@@ -1147,17 +1151,16 @@ function prepareForStartup() {
 
   // Manually hook up session and global history for the first browser
   // so that we don't have to load global history before bringing up a
   // window.
   // Wire up session and global history before any possible
   // progress notifications for back/forward button updating
   webNavigation.sessionHistory = Components.classes["@mozilla.org/browser/shistory;1"]
                                            .createInstance(Components.interfaces.nsISHistory);
-  var os = Components.classes["@mozilla.org/observer-service;1"].getService(Components.interfaces.nsIObserverService);
   os.addObserver(gBrowser.browsers[0], "browser:purge-session-history", false);
 
   // remove the disablehistory attribute so the browser cleans up, as
   // though it had done this work itself
   gBrowser.browsers[0].removeAttribute("disablehistory");
 
   // enable global history
   try {
@@ -1402,16 +1405,17 @@ function BrowserShutdown()
   catch(ex) {
     Components.utils.reportError(ex);
   }
 
   var os = Components.classes["@mozilla.org/observer-service;1"]
     .getService(Components.interfaces.nsIObserverService);
   os.removeObserver(gSessionHistoryObserver, "browser:purge-session-history");
   os.removeObserver(gXPInstallObserver, "xpinstall-install-blocked");
+  os.removeObserver(gMissingPluginInstaller.pluginCrashed, "plugin-crashed");
 
   try {
     gBrowser.removeProgressListener(window.XULBrowserWindow);
     gBrowser.removeTabsProgressListener(window.TabsProgressListener);
   } catch (ex) {
   }
 
   PlacesStarButton.uninit();
@@ -2531,21 +2535,44 @@ function BrowserReloadWithFlags(reloadFl
 
   try {
     webNav.reload(reloadFlags);
   } catch (e) {
   }
 }
 
 var PrintPreviewListener = {
+  _printPreviewTab: null,
+  _tabBeforePrintPreview: null,
+
+  getPrintPreviewBrowser: function () {
+    if (!this._printPreviewTab) {
+      this._tabBeforePrintPreview = gBrowser.selectedTab;
+      this._printPreviewTab = gBrowser.loadOneTab("about:blank",
+                                                  { inBackground: false });
+      gBrowser.selectedTab = this._printPreviewTab;
+    }
+    return gBrowser.getBrowserForTab(this._printPreviewTab);
+  },
+  getSourceBrowser: function () {
+    return this._tabBeforePrintPreview ?
+      this._tabBeforePrintPreview.linkedBrowser : gBrowser.selectedBrowser;
+  },
+  getNavToolbox: function () {
+    return gNavToolbox;
+  },
   onEnter: function () {
     gInPrintPreviewMode = true;
     this._toggleAffectedChrome();
   },
   onExit: function () {
+    gBrowser.selectedTab = this._tabBeforePrintPreview;
+    this._tabBeforePrintPreview = null;
+    gBrowser.removeTab(this._printPreviewTab);
+    this._printPreviewTab = null;
     gInPrintPreviewMode = false;
     this._toggleAffectedChrome();
   },
   _toggleAffectedChrome: function () {
     // chrome to toggle includes:
     //   (*) menubar
     //   (*) navigation bar
     //   (*) bookmarks toolbar
@@ -2567,51 +2594,44 @@ var PrintPreviewListener = {
   },
   _hideChrome: function () {
     this._chromeState = {};
 
     var sidebar = document.getElementById("sidebar-box");
     this._chromeState.sidebarOpen = !sidebar.hidden;
     this._sidebarCommand = sidebar.getAttribute("sidebarcommand");
 
-    this._chromeState.hadTabStrip = gBrowser.getStripVisibility();
-    gBrowser.setStripVisibilityTo(false);
+    gBrowser.mStrip.setAttribute("moz-collapsed", "true");
 
     var notificationBox = gBrowser.getNotificationBox();
     this._chromeState.notificationsOpen = !notificationBox.notificationsHidden;
     notificationBox.notificationsHidden = true;
 
     document.getElementById("sidebar").setAttribute("src", "about:blank");
     var statusbar = document.getElementById("status-bar");
     this._chromeState.statusbarOpen = !statusbar.hidden;
     statusbar.hidden = true;
 
     this._chromeState.findOpen = !gFindBar.hidden;
     gFindBar.close();
   },
   _showChrome: function () {
-    if (this._chromeState.hadTabStrip)
-      gBrowser.setStripVisibilityTo(true);
+    gBrowser.mStrip.removeAttribute("moz-collapsed");
 
     if (this._chromeState.notificationsOpen)
       gBrowser.getNotificationBox().notificationsHidden = false;
 
     if (this._chromeState.statusbarOpen)
       document.getElementById("status-bar").hidden = false;
 
     if (this._chromeState.findOpen)
       gFindBar.open();
   }
 }
 
-function getPPBrowser()
-{
-  return gBrowser;
-}
-
 function getMarkupDocumentViewer()
 {
   return gBrowser.markupDocumentViewer;
 }
 
 /**
  * Content area tooltip.
  * XXX - this must move into XBL binding/equiv! Do not want to pollute
@@ -5972,32 +5992,50 @@ function getPluginInfo(pluginElement)
     }
   }
 
   return {mimetype: tagMimetype, pluginsPage: pluginsPage};
 }
 
 var gMissingPluginInstaller = {
 
+  get CrashSubmit() {
+    delete this.CrashSubmit;
+    Cu.import("resource://gre/modules/CrashSubmit.jsm", this);
+    return this.CrashSubmit;
+  },
+
+  get crashReportHelpURL() {
+    delete this.crashReportHelpURL;
+    let url = formatURL("app.support.baseURL", true);
+    url += "plugin-crashed";
+    this.crashReportHelpURL = url;
+    return this.crashReportHelpURL;
+  },
+
   installSinglePlugin: function (aEvent) {
+    if (!aEvent.isTrusted)
+        return;
     var missingPluginsArray = {};
 
     var pluginInfo = getPluginInfo(aEvent.target);
     missingPluginsArray[pluginInfo.mimetype] = pluginInfo;
 
     if (missingPluginsArray) {
       openDialog("chrome://mozapps/content/plugins/pluginInstallerWizard.xul",
                  "PFSWindow", "chrome,centerscreen,resizable=yes",
                  {plugins: missingPluginsArray, browser: gBrowser.selectedBrowser});
     }
 
     aEvent.stopPropagation();
   },
 
   managePlugins: function (aEvent) {
+    if (!aEvent.isTrusted)
+        return;
     BrowserOpenAddonsMgr("plugins");
     aEvent.stopPropagation();
   },
 
   newMissingPlugin: function (aEvent) {
     // Since we are expecting also untrusted events, make sure
     // that the target is a plugin
     if (!(aEvent.target instanceof Ci.nsIObjectLoadingContent))
@@ -6009,16 +6047,21 @@ var gMissingPluginInstaller = {
     // so don't stomp on the page developers toes.
 
     if (aEvent.type != "PluginBlocklisted" &&
         aEvent.type != "PluginOutdated" &&
         !(aEvent.target instanceof HTMLObjectElement)) {
       aEvent.target.addEventListener("click",
                                      gMissingPluginInstaller.installSinglePlugin,
                                      true);
+      aEvent.target.addEventListener("keydown",
+                                     function(evt) { if (evt.keyCode == evt.DOM_VK_RETURN)
+                                                       gMissingPluginInstaller.installSinglePlugin(evt) },
+                                     true);
+                                                    
     }
 
     let hideBarPrefName = aEvent.type == "PluginOutdated" ?
                     "plugins.hide_infobar_for_outdated_plugin" :
                     "plugins.hide_infobar_for_missing_plugin";
     if (gPrefService.getBoolPref(hideBarPrefName))
       return;
 
@@ -6132,16 +6175,143 @@ var gMissingPluginInstaller = {
     // Since we are expecting also untrusted events, make sure
     // that the target is a plugin
     if (!(aEvent.target instanceof Ci.nsIObjectLoadingContent))
       return;
 
     aEvent.target.addEventListener("click",
                                    gMissingPluginInstaller.managePlugins,
                                    true);
+    aEvent.target.addEventListener("keydown",
+                                   function(evt) { if (evt.keyCode == evt.DOM_VK_RETURN)
+                                                     gMissingPluginInstaller.managePlugins(evt) },
+                                   true);
+  },
+
+  // Crashed-plugin observer. Notified once per plugin crash, before events
+  // are dispatched to individual plugin instances.
+  pluginCrashed : function(subject, topic, data) {
+    let propertyBag = subject;
+    if (!(propertyBag instanceof Ci.nsIPropertyBag2) ||
+        !(propertyBag instanceof Ci.nsIWritablePropertyBag2))
+     return;
+
+#ifdef MOZ_CRASHREPORTER
+    let minidumpID = subject.getPropertyAsAString("minidumpID");
+    let submitReports = gCrashReporter.submitReports;
+    // The crash reporter wants a DOM element it can append an IFRAME to,
+    // which it uses to submit a form. Let's just give it gBrowser.
+    if (submitReports)
+      gMissingPluginInstaller.CrashSubmit.submit(minidumpID, gBrowser, null, null);
+    propertyBag.setPropertyAsBool("submittedCrashReport", submitReports);
+#endif
+  },
+
+  pluginInstanceCrashed: function (aEvent) {
+    // Evil content could fire a fake event at us, ignore them.
+    if (!aEvent.isTrusted)
+      return;
+
+    if (!(aEvent instanceof Ci.nsIDOMDataContainerEvent))
+      return;
+
+    let submittedReport = aEvent.getData("submittedCrashReport");
+    let pluginName      = aEvent.getData("pluginName");
+
+    // We're expecting this to be a plugin.
+    let plugin = aEvent.target;
+    if (!(plugin instanceof Ci.nsIObjectLoadingContent))
+      return;
+
+    // Force a style flush, so that we ensure our binding is attached.
+    plugin.clientTop;
+
+    let messageString = gNavigatorBundle.getFormattedString("crashedpluginsMessage.title", [pluginName]);
+
+    //
+    // Configure the crashed-plugin placeholder.
+    //
+    let doc = plugin.ownerDocument;
+    let overlay = doc.getAnonymousElementByAttribute(plugin, "class", "mainBox");
+
+    // The binding has role="link" here, since missing/disabled/blocked
+    // plugin UI has a onclick handler on the whole thing. This isn't needed
+    // for the plugin-crashed UI, because we use actual HTML links in the text.
+    overlay.removeAttribute("role");
+
+#ifdef MOZ_CRASHREPORTER
+    let helpClass = submittedReport ? "submitLink" : "notSubmitLink";
+    let helpLink = doc.getAnonymousElementByAttribute(plugin, "class", helpClass);
+    helpLink.href = gMissingPluginInstaller.crashReportHelpURL;
+    let showClass = submittedReport ? "msg msgSubmitted" : "msg msgNotSubmitted";
+    let textToShow = doc.getAnonymousElementByAttribute(plugin, "class", showClass);
+    textToShow.style.display = "block";
+#endif
+
+    let crashText = doc.getAnonymousElementByAttribute(plugin, "class", "msg msgCrashed");
+    crashText.textContent = messageString;
+
+    let link = doc.getAnonymousElementByAttribute(plugin, "class", "reloadLink");
+    link.addEventListener("click", function(e) { if (e.isTrusted) browser.reload(); }, true);
+
+    let browser = gBrowser.getBrowserForDocument(plugin.ownerDocument
+                                                       .defaultView.top.document);
+    let notificationBox = gBrowser.getNotificationBox(browser);
+
+    // Is the <object>'s size too small to hold what we want to show?
+    let pluginRect = plugin.getBoundingClientRect();
+    // XXX bug 446693. The text-shadow on the submitted-report text at
+    //     the bottom causes scrollHeight to be larger than it should be.
+    let isObjectTooSmall = (overlay.scrollWidth > pluginRect.width) ||
+                           (overlay.scrollHeight - 5 > pluginRect.height);
+    if (isObjectTooSmall) {
+        // Hide the overlay's contents. Use visibility style, so that it
+        // doesn't collapse down to 0x0.
+        overlay.style.visibility = "hidden";
+        // If another plugin on the page was large enough to show our UI, we
+        // don't want to show a notification bar.
+        if (!doc.mozNoPluginCrashedNotification)
+          showNotificationBar();
+    } else {
+        // If a previous plugin on the page was too small and resulted in
+        // adding a notification bar, then remove it because this plugin
+        // instance it big enough to serve as in-content notification.
+        hideNotificationBar();
+        doc.mozNoPluginCrashedNotification = true;
+    }
+
+    function hideNotificationBar() {
+      let notification = notificationBox.getNotificationWithValue("plugin-crashed");
+      if (notification)
+        notificationBox.removeNotification(notification, true);
+    }
+
+    function showNotificationBar() {
+      // If there's already an existing notification bar, don't do anything.
+      let notification = notificationBox.getNotificationWithValue("plugin-crashed");
+      if (notification)
+        return;
+
+      // Configure the notification bar
+      let priority = notificationBox.PRIORITY_WARNING_MEDIUM;
+      let iconURL = "chrome://mozapps/skin/plugins/pluginGeneric-16.png";
+      let label = gNavigatorBundle.getString("crashedpluginsMessage.reloadButton.label");
+      let accessKey = gNavigatorBundle.getString("crashedpluginsMessage.reloadButton.accesskey");
+
+      let buttons = [{
+        label: label,
+        accessKey: accessKey,
+        popup: null,
+        callback: function() { browser.reload(); },
+      }];
+
+      let notification = notificationBox.appendNotification(messageString, "plugin-crashed",
+                                                            iconURL, priority, buttons);
+    }
+
   },
 
   refreshBrowser: function (aEvent) {
     // browser elements are anonymous so we can't just use target.
     var browser = aEvent.originalTarget;
     var notificationBox = gBrowser.getNotificationBox(browser);
     var notification = notificationBox.getNotificationWithValue("missing-plugins");
 
--- a/browser/base/content/test/Makefile.in
+++ b/browser/base/content/test/Makefile.in
@@ -77,16 +77,17 @@ include $(topsrcdir)/config/rules.mk
 #   browser_sanitize-download-history.js is bug 432425
 #
 # browser_sanitizeDialog_treeView.js is disabled until the tree view is added
 # back to the clear recent history dialog (santize.xul), if it ever is (bug
 # 480169)
 
 _BROWSER_FILES = \
                  browser_NetworkPrioritizer.js \
+                 browser_allTabsPanel.js \
                  browser_alltabslistener.js \
                  browser_bug304198.js \
                  browser_bug321000.js \
                  title_test.svg \
                  browser_bug329212.js \
                  browser_bug356571.js \
                  browser_bug386835.js \
                  browser_bug405137.js \
new file mode 100644
--- /dev/null
+++ b/browser/base/content/test/browser_allTabsPanel.js
@@ -0,0 +1,154 @@
+function test() {
+  waitForExplicitFinish();
+  allTabs.init();
+  nextSequence();
+}
+
+var sequences = 3;
+var chars = "ABCDEFGHI";
+var closedTabs;
+var history;
+var steps;
+var whenOpen = [
+  startSearch,
+  clearSearch, clearSearch,
+  closeTab,
+  moveTab,
+  closePanel,
+];
+var whenClosed = [
+  openPanel, openPanel, openPanel, openPanel, openPanel, openPanel,
+  closeTab, closeTab, closeTab,
+  moveTab, moveTab, moveTab,
+  selectTab, selectTab,
+  undoCloseTab,
+  openTab,
+];
+
+function rand(min, max) {
+  return min + Math.floor(Math.random() * (max - min + 1));
+}
+function pickOne(array) {
+  return array[rand(0, array.length - 1)];
+}
+function pickOneTab() {
+  var tab = pickOne(gBrowser.tabContainer.childNodes);
+  return [tab, Array.indexOf(gBrowser.tabContainer.childNodes, tab)];
+}
+function nextSequence() {
+  while (gBrowser.browsers.length > 1)
+    gBrowser.removeCurrentTab();
+  if (sequences-- <= 0) {
+    allTabs.close();
+    gBrowser.addTab();
+    gBrowser.removeCurrentTab();
+    finish();
+    return;
+  }
+  closedTabs = 0;
+  steps = rand(10, 20);
+  var initialTabs = "";
+  while (gBrowser.browsers.length < rand(3, 20)) {
+    let tabChar = pickOne(chars);
+    initialTabs += tabChar;
+    gBrowser.addTab("data:text/plain," + tabChar);
+  }
+  history = [initialTabs];
+  gBrowser.removeCurrentTab();
+  next();
+}
+function next() {
+  executeSoon(function () {
+    is(allTabs.previews.length, gBrowser.browsers.length,
+       history.join(", "));
+    if (steps-- <= 0) {
+      nextSequence();
+      return;
+    }
+    var step;
+    var rv;
+    do {
+      step = pickOne(allTabs.isOpen ? whenOpen : whenClosed);
+      rv = step();
+    } while (rv === false);
+    history.push(step.name + (rv !== true && rv !== undefined ? " " + rv : ""));
+  });
+}
+
+function openPanel() {
+  if (allTabs.isOpen)
+    return false;
+  allTabs.panel.addEventListener("popupshown", function () {
+    allTabs.panel.removeEventListener("popupshown", arguments.callee, false);
+    next();
+  }, false);
+  allTabs.open();
+  return true;
+}
+
+function closePanel() {
+  allTabs.panel.addEventListener("popuphidden", function () {
+    allTabs.panel.removeEventListener("popuphidden", arguments.callee, false);
+    next();
+  }, false);
+  allTabs.close();
+}
+
+function closeTab() {
+  if (gBrowser.browsers.length == 1)
+    return false;
+  var [tab, index] = pickOneTab();
+  gBrowser.removeTab(tab);
+  closedTabs++;
+  next();
+  return index;
+}
+
+function startSearch() {
+  allTabs.filterField.value = pickOne(chars);
+  allTabs.filter();
+  next();
+  return allTabs.filterField.value;
+}
+
+function clearSearch() {
+  if (!allTabs.filterField.value)
+    return false;
+  allTabs.filterField.value = "";
+  allTabs.filter();
+  next();
+  return true;
+}
+
+function undoCloseTab() {
+  if (!closedTabs)
+    return false;
+  window.undoCloseTab(0);
+  closedTabs--;
+  next();
+  return true;
+}
+
+function selectTab() {
+  var [tab, index] = pickOneTab();
+  gBrowser.selectedTab = tab;
+  next();
+  return index;
+}
+
+function openTab() {
+  BrowserOpenTab();
+  next();
+}
+
+function moveTab() {
+  if (gBrowser.browsers.length == 1)
+    return false;
+  var [tab, currentIndex] = pickOneTab();
+  do {
+    var [, newIndex] = pickOneTab();
+  } while (newIndex == currentIndex);
+  gBrowser.moveTabTo(tab, newIndex);
+  next();
+  return currentIndex + "->" + newIndex;
+}
--- a/browser/components/preferences/advanced.js
+++ b/browser/components/preferences/advanced.js
@@ -61,16 +61,19 @@ var gAdvancedPane = {
     }
 
 #ifdef MOZ_UPDATER
     this.updateAppUpdateItems();
     this.updateAutoItems();
     this.updateModeItems();
 #endif
     this.updateOfflineApps();
+#ifdef MOZ_CRASHREPORTER
+    this.initSubmitCrashes();
+#endif
   },
 
   /**
    * Stores the identity of the current tab in preferences so that the selected
    * tab can be persisted between openings of the preferences window.
    */
   tabSelectionChanged: function ()
   {
@@ -134,16 +137,45 @@ var gAdvancedPane = {
    * unchanged and represents a value not strictly allowed in UI.
    */
   writeCheckSpelling: function ()
   {
     var checkbox = document.getElementById("checkSpelling");
     return checkbox.checked ? (this._storedSpellCheck == 2 ? 2 : 1) : 0;
   },
 
+  /**
+   *
+   */
+  initSubmitCrashes: function ()
+  {
+    var checkbox = document.getElementById("submitCrashesBox");
+    try {
+      var cr = Components.classes["@mozilla.org/toolkit/crash-reporter;1"].
+               getService(Components.interfaces.nsICrashReporter);
+      checkbox.checked = cr.submitReports;
+    } catch (e) {
+      checkbox.style.display = "none";
+    }
+  },
+
+  /**
+   *
+   */
+  updateSubmitCrashes: function ()
+  {
+    var checkbox = document.getElementById("submitCrashesBox");
+    try {
+      var cr = Components.classes["@mozilla.org/toolkit/crash-reporter;1"].
+               getService(Components.interfaces.nsICrashReporter);
+      cr.submitReports = checkbox.checked;
+    } catch (e) { }
+  },
+
+
   // NETWORK TAB
 
   /*
    * Preferences:
    *
    * browser.cache.disk.capacity
    * - the size of the browser cache in KB
    */
--- a/browser/components/preferences/advanced.xul
+++ b/browser/components/preferences/advanced.xul
@@ -179,28 +179,33 @@
                       accesskey="&checkSpelling.accesskey;"
                       onsyncfrompreference="return gAdvancedPane.readCheckSpelling();"
                       onsynctopreference="return gAdvancedPane.writeCheckSpelling();"
                       preference="layout.spellcheckDefault"/>
           </groupbox>
 
 #ifdef HAVE_SHELL_SERVICE
           <!-- System Defaults -->
-          <groupbox id="systemDefaultsGroup" orient="horizontal">
+          <groupbox id="systemDefaultsGroup" orient="vertical">
             <caption label="&systemDefaults.label;"/>
 
             <hbox id="checkDefaultBox" align="center" flex="1">      
               <checkbox id="alwaysCheckDefault" preference="browser.shell.checkDefaultBrowser"
                         label="&alwaysCheckDefault.label;" accesskey="&alwaysCheckDefault.accesskey;"
                         flex="1"/>
               <button id="checkDefaultButton"
                       label="&checkNow.label;" accesskey="&checkNow.accesskey;"
                       oncommand="gAdvancedPane.checkNow()"
                       preference="pref.general.disable_button.default_browser"/>
             </hbox>
+#ifdef MOZ_CRASHREPORTER
+            <checkbox id="submitCrashesBox" flex="1"
+                      oncommand="gAdvancedPane.updateSubmitCrashes();"
+                      label="&submitCrashes.label;" accesskey="&submitCrashes.accesskey;"/>
+#endif
           </groupbox>
 #endif
         </tabpanel>
 
         <!-- Network -->
         <tabpanel id="networkPanel" orient="vertical">
 
            <!-- Connection -->
--- a/browser/components/wintaskbar/WindowsPreviewPerTab.jsm
+++ b/browser/components/wintaskbar/WindowsPreviewPerTab.jsm
@@ -414,17 +414,17 @@ TabWindow.prototype = {
   },
   get height () {
     return this.win.innerHeight;
   },
 
   // Invoked when the given tab is added to this window
   newTab: function (tab) {
     let controller = new PreviewController(this, tab);
-    let preview = AeroPeek.taskbar.createTaskbarTabPreview(this.tabbrowser.docShell, controller);
+    let preview = AeroPeek.taskbar.createTaskbarTabPreview(tab.linkedBrowser.docShell, controller);
     preview.title = tab.label;
     preview.tooltip = tab.label;
     preview.visible = AeroPeek.enabled;
     preview.active = this.tabbrowser.selectedTab == tab;
     // Grab the default favicon
     getFaviconAsImage(null, function (img) {
       // It is possible that we've already gotten the real favicon, so make sure
       // we have not set one before setting this default one.
@@ -468,17 +468,21 @@ TabWindow.prototype = {
     this.updateTabOrdering();
   },
 
   previewFromTab: function (tab) {
     return this.previews[tab._tPos];
   },
 
   updateTabOrdering: function () {
-    for (let i = 0; i < this.previews.length; i++) {
+    // Since the internal taskbar array has not yet been updated we must force
+    // on it the sorting order of our local array.  To do so we must walk
+    // the local array backwards, otherwise we would send move requests in the
+    // wrong order.  See bug 522610 for details.
+    for (let i = this.previews.length - 1; i >= 0; i--) {
       let p = this.previews[i];
       let next = i == this.previews.length - 1 ? null : this.previews[i+1];
       p.move(next);
     }
   },
 
   //// nsIDOMEventListener
   handleEvent: function (evt) {
--- a/browser/installer/package-manifest.in
+++ b/browser/installer/package-manifest.in
@@ -334,16 +334,17 @@
 @BINPATH@/components/nsFormAutoComplete.js
 @BINPATH@/components/contentSecurityPolicy.js
 #ifdef XP_MACOSX
 @BINPATH@/components/libalerts_s.dylib
 #endif
 #ifdef MOZ_ENABLE_DBUS
 @BINPATH@/components/@DLL_PREFIX@dbusservice@DLL_SUFFIX@
 #endif
+@BINPATH@/components/nsINIProcessor.js
 
 ; Modules
 @BINPATH@/modules/*
 
 ; Safe Browsing
 @BINPATH@/components/nsSafebrowsingApplication.js
 @BINPATH@/components/nsUrlClassifierListManager.js
 @BINPATH@/components/nsUrlClassifierLib.js
--- a/browser/locales/en-US/chrome/browser/browser.properties
+++ b/browser/locales/en-US/chrome/browser/browser.properties
@@ -69,16 +69,19 @@ missingpluginsMessage.button.accesskey=I
 outdatedpluginsMessage.title=Some plugins used by this page are out of date.
 outdatedpluginsMessage.updateButton.label=Update Plugins…
 outdatedpluginsMessage.updateButton.accesskey=U
 blockedpluginsMessage.title=Some plugins required by this page have been blocked for your protection.
 blockedpluginsMessage.infoButton.label=Details…
 blockedpluginsMessage.infoButton.accesskey=D
 blockedpluginsMessage.searchButton.label=Update Plugins…
 blockedpluginsMessage.searchButton.accesskey=U
+crashedpluginsMessage.title=The %S plugin has crashed.
+crashedpluginsMessage.reloadButton.label=Reload page
+crashedpluginsMessage.reloadButton.accesskey=R
 
 # Sanitize
 # LOCALIZATION NOTE (sanitizeDialog2.everything.title): When "Time range to
 # clear" is set to "Everything", the Clear Recent History dialog's title is
 # changed to this.  See UI mockup and comment 11 at bug 480169 -->
 sanitizeDialog2.everything.title=Clear All History
 sanitizeButtonOK=Clear Now
 # LOCALIZATION NOTE (sanitizeEverythingWarning2): Warning that appears when
--- a/browser/locales/en-US/chrome/browser/preferences/advanced.dtd
+++ b/browser/locales/en-US/chrome/browser/preferences/advanced.dtd
@@ -20,16 +20,18 @@
 <!ENTITY checkSpelling.label             "Check my spelling as I type">
 <!ENTITY checkSpelling.accesskey         "t">
 
 <!ENTITY systemDefaults.label            "System Defaults">
 <!ENTITY alwaysCheckDefault.label        "Always check to see if &brandShortName; is the default browser on startup"><!--XXX-->
 <!ENTITY alwaysCheckDefault.accesskey    "w">
 <!ENTITY checkNow.label                  "Check Now">
 <!ENTITY checkNow.accesskey              "N">
+<!ENTITY submitCrashes.label             "Submit crash reports">
+<!ENTITY submitCrashes.accesskey         "S">
 
 <!ENTITY networkTab.label                "Network">
 
 <!ENTITY connection.label                "Connection">
 
 <!ENTITY connectionDesc.label            "Configure how &brandShortName; connects to the Internet">
 <!ENTITY connectionSettings.label        "Settings…">
 <!ENTITY connectionSettings.accesskey    "e">
--- a/config/autoconf.mk.in
+++ b/config/autoconf.mk.in
@@ -618,25 +618,19 @@ WINCE_SDK_DIR   = @WINCE_SDK_DIR@
 OGLES_SDK_DIR   = @OGLES_SDK_DIR@
 
 WINCE_WINDOWS_MOBILE = @WINCE_WINDOWS_MOBILE@
 
 HAS_OGLES = @HAS_OGLES@
 
 MOZ_DISTRIBUTION_ID = @MOZ_DISTRIBUTION_ID@
 
-NS_OSSO 	= @NS_OSSO@
-MOZ_PLATFORM_HILDON = @MOZ_PLATFORM_HILDON@
-
-LIBHILDONMIME_CFLAGS	= @LIBHILDONMIME_CFLAGS@
-LIBHILDONMIME_LIBS	= @LIBHILDONMIME_LIBS@
-LIBOSSO_CFLAGS 	= @LIBOSSO_CFLAGS@
-LIBOSSO_LIBS 	= @LIBOSSO_LIBS@
-LIBHILDONFM_CFLAGS	= @LIBHILDONFM_CFLAGS@
-LIBHILDONFM_LIBS	= @LIBHILDONFM_LIBS@
+MOZ_PLATFORM_MAEMO = @MOZ_PLATFORM_MAEMO@
+MOZ_PLATFORM_MAEMO_CFLAGS	= @MOZ_PLATFORM_MAEMO_CFLAGS@
+MOZ_PLATFORM_MAEMO_LIBS 	= @MOZ_PLATFORM_MAEMO_LIBS@
 
 MOZ_ENABLE_LIBCONIC = @MOZ_ENABLE_LIBCONIC@
 LIBCONIC_CFLAGS     = @LIBCONIC_CFLAGS@
 LIBCONIC_LIBS       = @LIBCONIC_LIBS@
 
 MACOS_SDK_DIR	= @MACOS_SDK_DIR@
 NEXT_ROOT	= @NEXT_ROOT@
 GCC_VERSION	= @GCC_VERSION@
--- a/config/rules.mk
+++ b/config/rules.mk
@@ -375,16 +375,17 @@ ifndef TARGETS
 TARGETS			= $(LIBRARY) $(SHARED_LIBRARY) $(PROGRAM) $(SIMPLE_PROGRAMS) $(HOST_LIBRARY) $(HOST_PROGRAM) $(HOST_SIMPLE_PROGRAMS) $(JAVA_LIBRARY)
 endif
 
 ifndef OBJS
 _OBJS			= \
 	$(JRI_STUB_CFILES) \
 	$(addsuffix .$(OBJ_SUFFIX), $(JMC_GEN)) \
 	$(CSRCS:.c=.$(OBJ_SUFFIX)) \
+	$(SSRCS:.S=.$(OBJ_SUFFIX)) \
 	$(patsubst %.cc,%.$(OBJ_SUFFIX),$(CPPSRCS:.cpp=.$(OBJ_SUFFIX))) \
 	$(CMSRCS:.m=.$(OBJ_SUFFIX)) \
 	$(CMMSRCS:.mm=.$(OBJ_SUFFIX)) \
 	$(ASFILES:.$(ASM_SUFFIX)=.$(OBJ_SUFFIX))
 OBJS	= $(strip $(_OBJS))
 endif
 
 ifndef HOST_OBJS
--- a/config/system-headers
+++ b/config/system-headers
@@ -1004,22 +1004,20 @@ libsn/sn-monitor.h
 libsn/sn-util.h
 #endif
 #if MOZ_NATIVE_HUNSPELL==1
 hunspell.hxx
 #endif
 #if MOZ_NATIVE_BZ2==1
 bzlib.h
 #endif
-#ifdef MOZ_PLATFORM_HILDON
+#if MOZ_PLATFORM_MAEMO==5
 hildon-uri.h
 hildon-mime.h
 hildon-file-chooser-dialog.h
-#endif
-#ifdef NS_OSSO
 libosso.h
 osso-mem.h
 #endif
 #ifdef MOZ_ENABLE_GIO
 gio/gio.h
 #endif
 #ifdef MOZ_ENABLE_LIBCONIC
 conic/conicconnection.h
--- a/configure.in
+++ b/configure.in
@@ -398,38 +398,38 @@ else
     AC_PROG_CXX
     AC_PROG_RANLIB
     MOZ_PATH_PROGS(AS, $AS as, $CC)
     AC_CHECK_PROGS(AR, ar, :)
     AC_CHECK_PROGS(LD, ld, :)
     AC_CHECK_PROGS(STRIP, strip, :)
     AC_CHECK_PROGS(WINDRES, windres, :)
     if test -z "$HOST_CC"; then
-        HOST_CC="$CC"
+        HOST_CC='$(CC)'
     fi
     if test -z "$HOST_CFLAGS"; then
-        HOST_CFLAGS="$CFLAGS"
+        HOST_CFLAGS='$(CFLAGS)'
     fi
     if test -z "$HOST_CXX"; then
-        HOST_CXX="$CXX"
+        HOST_CXX='$(CXX)'
     fi
     if test -z "$HOST_CXXFLAGS"; then
-        HOST_CXXFLAGS="$CXXFLAGS"
+        HOST_CXXFLAGS='$(CXXFLAGS)'
     fi
     if test -z "$HOST_LDFLAGS"; then
-        HOST_LDFLAGS="$LDFLAGS"
+        HOST_LDFLAGS='$(LDFLAGS)'
     fi
     if test -z "$HOST_RANLIB"; then
-        HOST_RANLIB="$RANLIB"
+        HOST_RANLIB='$(RANLIB)'
     fi
     if test -z "$HOST_AR"; then
-        HOST_AR="$AR"
+        HOST_AR='$(AR)'
     fi
     if test -z "$HOST_AR_FLAGS"; then
-        HOST_AR_FLAGS="$AR_FLAGS"
+        HOST_AR_FLAGS='$(AR_FLAGS)'
     fi
 fi
 
 GNU_AS=
 GNU_LD=
 GNU_CC=
 GNU_CXX=
 CC_VERSION='N/A'
@@ -1725,17 +1725,16 @@ case "$host" in
         ;;
     esac
     ;;
 
 *-darwin*)
     HOST_CFLAGS="$HOST_CFLAGS -DXP_UNIX -DXP_MACOSX -DNO_X11"
     HOST_NSPR_MDCPUCFG='\"md/_darwin.cfg\"'
     HOST_OPTIMIZE_FLAGS="${HOST_OPTIMIZE_FLAGS=-O3}"
-    MOZ_FIX_LINK_PATHS='-Wl,-executable_path,$(LIBXUL_DIST)/bin'
     ;;
 
 *-linux*|*-kfreebsd*-gnu)
     HOST_CFLAGS="$HOST_CFLAGS -DXP_UNIX"
     HOST_NSPR_MDCPUCFG='\"md/_linux.cfg\"'
     HOST_OPTIMIZE_FLAGS="${HOST_OPTIMIZE_FLAGS=-O3}"
     ;;
 
@@ -1911,16 +1910,17 @@ case "$target" in
             AC_MSG_RESULT([yes])
             MOZ_OPTIMIZE_LDFLAGS="-Wl,-dead_strip"
         else
             AC_MSG_RESULT([no])
         fi
         
         LDFLAGS=$_SAVE_LDFLAGS
     fi
+    MOZ_FIX_LINK_PATHS='-Wl,-executable_path,$(LIBXUL_DIST)/bin'
     ;;
 
 *-freebsd*)
     if test `test -x /usr/bin/objformat && /usr/bin/objformat || echo elf` != "elf"; then
 	DLL_SUFFIX=".so.1.0"
 	DSO_LDOPTS="-shared"
     fi
     if test ! "$GNU_CC"; then
@@ -4896,20 +4896,20 @@ cairo-os2)
 
 cairo-cocoa)
     MOZ_WIDGET_TOOLKIT=cocoa
     AC_DEFINE(MOZ_WIDGET_COCOA)
     MOZ_USER_DIR="Mozilla"
     AC_DEFINE(XP_MACOSX)
     TK_LIBS='-framework Carbon -framework CoreAudio -framework AudioToolbox -framework AudioUnit -framework AddressBook'
     TK_CFLAGS="-DNO_X11"
-    LDFLAGS="$LDFLAGS -framework Cocoa"
+    LDFLAGS="$LDFLAGS -framework Cocoa -lobjc"
     CFLAGS="$CFLAGS $TK_CFLAGS"
     CXXFLAGS="$CXXFLAGS $TK_CFLAGS"
-    LIBXUL_LIBS='$(XPCOM_FROZEN_LDOPTS) $(LIBXUL_DIST)/bin/XUL -lobjc'
+    LIBXUL_LIBS='$(XPCOM_FROZEN_LDOPTS) $(LIBXUL_DIST)/bin/XUL'
     MOZ_FS_LAYOUT=bundle
     MOZ_WEBGL=1
     ;;
 esac
 
 if test "$MOZ_ENABLE_XREMOTE"; then
     AC_DEFINE(MOZ_ENABLE_XREMOTE)
 fi
@@ -6403,57 +6403,88 @@ if test "$MOZ_ENABLE_LIBCONIC"; then
     AC_DEFINE(MOZ_ENABLE_LIBCONIC)
 fi
 
 AC_SUBST(MOZ_ENABLE_LIBCONIC)
 AC_SUBST(LIBCONIC_CFLAGS)
 AC_SUBST(LIBCONIC_LIBS)
  
 dnl ========================================================
-dnl = Hildon and OSSO checks
-dnl ========================================================
-PKG_CHECK_MODULES(LIBHILDONMIME,libhildonmime,
-                  MOZ_PLATFORM_HILDON=1,
-                  MOZ_PLATFORM_HILDON=)
-if test $MOZ_PLATFORM_HILDON; then
-   AC_DEFINE(MOZ_PLATFORM_HILDON)
-   X11_COMPOSITED_PLUGINS="yes"
-fi
-AC_SUBST(LIBHILDONMIME_CFLAGS)
-AC_SUBST(LIBHILDONMIME_LIBS)
-
-if test "$X11_COMPOSITED_PLUGINS" = "yes"; then
-    dnl if we have Xcomposite we should also have Xdamage and Xfixes
-    AC_CHECK_HEADERS([X11/extensions/Xdamage.h], [],
-                     [AC_MSG_ERROR([Couldn't find X11/extentsions/Xdamage.h which is required for composited plugins.])])
-    AC_CHECK_LIB(Xcomposite, XCompositeRedirectWindow, [XCOMPOSITE_LIBS="-lXcomposite -lXdamage -lXfixes"],
-                 [MISSING_X="$MISSING_X -lXcomposite"], $XLIBS)
-fi
-AC_SUBST(XCOMPOSITE_LIBS)
-
-PKG_CHECK_MODULES(LIBOSSO,libosso,
-                  NS_OSSO=1,
-                  NS_OSSO=)
-
-if test $NS_OSSO; then
-    if test -z "$MOZ_ENABLE_DBUS"; then
-        AC_MSG_ERROR([DBus is required when building for OSSO])
-    fi
-    AC_DEFINE(NS_OSSO)
-    MOZ_GFX_OPTIMIZE_MOBILE=1
-    MOZ_WEBGL_GLX=
-fi
-AC_SUBST(LIBOSSO_CFLAGS)
-AC_SUBST(LIBOSSO_LIBS)
-
-PKG_CHECK_MODULES(LIBHILDONFM,hildon-fm-2,
-                  NS_HILDONFM=1,
-                  NS_HILDONFM=)
-AC_SUBST(LIBHILDONFM_CFLAGS)
-AC_SUBST(LIBHILDONFM_LIBS)
+dnl = Maemo checks
+dnl ========================================================
+
+MAEMO_SDK_TARGET_VER=-1
+
+MOZ_ARG_WITH_STRING(maemo-version,
+[  --with-maemo-version=MAEMO_SDK_TARGET_VER
+                        Maemo SDK Version],
+  MAEMO_SDK_TARGET_VER=$withval)
+
+case "$MAEMO_SDK_TARGET_VER" in
+5)
+    MOZ_PLATFORM_MAEMO=5
+    ;;
+
+6)
+    MOZ_PLATFORM_MAEMO=6
+    ;;
+
+-1)
+    dnl We aren't compiling for Maemo, move on.
+    ;;
+*)
+    AC_MSG_ERROR([Unknown Maemo Version.  Try setting --with-maemo-version to 5 or 6.])
+    ;;
+esac
+
+if test $MOZ_PLATFORM_MAEMO; then
+   AC_DEFINE_UNQUOTED([MOZ_PLATFORM_MAEMO], $MOZ_PLATFORM_MAEMO)
+
+   if test -z "$MOZ_ENABLE_DBUS"; then
+       AC_MSG_ERROR([DBus is required when building for Maemo])
+   fi
+   
+   MOZ_GFX_OPTIMIZE_MOBILE=1
+   MOZ_WEBGL_GLX=
+
+   if test $MOZ_PLATFORM_MAEMO = 5; then
+      dnl if we have Xcomposite we should also have Xdamage and Xfixes
+      AC_CHECK_HEADERS([X11/extensions/Xdamage.h], [],
+                       [AC_MSG_ERROR([Couldn't find X11/extensions/Xdamage.h which is required for composited plugins.])])
+      AC_CHECK_LIB(Xcomposite, XCompositeRedirectWindow, [XCOMPOSITE_LIBS="-lXcomposite -lXdamage -lXfixes"],
+                   [MISSING_X="$MISSING_X -lXcomposite"], $XLIBS)
+
+      AC_SUBST(XCOMPOSITE_LIBS)
+
+      PKG_CHECK_MODULES(LIBHILDONMIME,libhildonmime, _LIB_FOUND=1, _LIB_FOUND=)
+      MOZ_PLATFORM_MAEMO_LIBS="$MOZ_PLATFORM_MAEMO_LIBS $LIBHILDONMIME_LIBS"
+      MOZ_PLATFORM_MAEMO_CFLAGS="$MOZ_PLATFORM_MAEMO_CFLAGS $LIBHILDONMIME_CFLAGS"
+      if test -z "$_LIB_FOUND"; then
+         AC_MSG_ERROR([Hildon Mime is required when building for Maemo])
+      fi
+
+
+      PKG_CHECK_MODULES(LIBOSSO,libosso, _LIB_FOUND=1, _LIB_FOUND=)
+      MOZ_PLATFORM_MAEMO_LIBS="$MOZ_PLATFORM_MAEMO_LIBS $LIBOSSO_LIBS"
+      MOZ_PLATFORM_MAEMO_CFLAGS="$MOZ_PLATFORM_MAEMO_CFLAGS $LIBOSSO_CFLAGS"
+      if test -z "$_LIB_FOUND"; then
+         AC_MSG_ERROR([LibOSSO is required when building for Maemo])
+      fi
+
+      PKG_CHECK_MODULES(LIBHILDONFM,hildon-fm-2, _LIB_FOUND=1, _LIB_FOUND=)
+      MOZ_PLATFORM_MAEMO_LIBS="$MOZ_PLATFORM_MAEMO_LIBS $LIBHILDONFM_LIBS"
+      MOZ_PLATFORM_MAEMO_CFLAGS="$MOZ_PLATFORM_MAEMO_CFLAGS $LIBHILDONFM_CFLAGS"
+      if test -z "$_LIB_FOUND"; then
+         AC_MSG_ERROR([Hildon FM-2 is required when building for Maemo])
+      fi
+   fi
+
+   AC_SUBST(MOZ_PLATFORM_MAEMO_LIBS)
+   AC_SUBST(MOZ_PLATFORM_MAEMO_CFLAGS)
+fi
 
 dnl ========================================================
 dnl = faststripe theme
 dnl ========================================================
 MOZ_ARG_ENABLE_BOOL(faststripe,
 [  --enable-faststripe  Use faststripe theme],
     MOZ_THEME_FASTSTRIPE=1,
     MOZ_THEME_FASTSTRIPE= )
@@ -8013,19 +8044,17 @@ AC_SUBST(RCFLAGS)
 AC_SUBST(WINDRES)
 AC_SUBST(IMPLIB)
 AC_SUBST(FILTER)
 AC_SUBST(BIN_FLAGS)
 AC_SUBST(NS_USE_NATIVE)
 AC_SUBST(MOZ_WIDGET_TOOLKIT)
 AC_SUBST(MOZ_UPDATE_XTERM)
 AC_SUBST(MINIMO)
-AC_SUBST(MOZ_PLATFORM_HILDON)
-AC_SUBST(NS_OSSO)
-AC_SUBST(NS_MAEMO_LOCATION)
+AC_SUBST(MOZ_PLATFORM_MAEMO)
 AC_SUBST(MOZ_AUTH_EXTENSION)
 AC_SUBST(MOZ_MATHML)
 AC_SUBST(MOZ_PERMISSIONS)
 AC_SUBST(MOZ_XTF)
 AC_SUBST(MOZ_NO_INSPECTOR_APIS)
 AC_SUBST(MOZ_PREF_EXTENSIONS)
 AC_SUBST(MOZ_SVG)
 AC_SUBST(MOZ_SMIL)
--- a/content/base/public/nsContentUtils.h
+++ b/content/base/public/nsContentUtils.h
@@ -41,30 +41,30 @@
 
 #ifndef nsContentUtils_h___
 #define nsContentUtils_h___
 
 #include "jsprvtd.h"
 #include "jsnum.h"
 #include "nsAString.h"
 #include "nsIStatefulFrame.h"
-#include "nsIPref.h"
 #include "nsINodeInfo.h"
 #include "nsNodeInfoManager.h"
 #include "nsContentList.h"
 #include "nsDOMClassInfoID.h"
 #include "nsIClassInfo.h"
 #include "nsIDOM3Node.h"
 #include "nsDataHashtable.h"
 #include "nsIScriptRuntime.h"
 #include "nsIScriptGlobalObject.h"
 #include "nsIDOMEvent.h"
 #include "nsTArray.h"
 #include "nsTextFragment.h"
 #include "nsReadableUtils.h"
+#include "nsIPrefBranch2.h"
 
 struct nsNativeKeyEvent; // Don't include nsINativeKeyBindings.h here: it will force strange compilation error!
 
 class nsIDOMScriptObjectFactory;
 class nsIXPConnect;
 class nsINode;
 class nsIContent;
 class nsIDOMNode;
@@ -79,50 +79,55 @@ class nsIThreadJSContextStack;
 class nsIParserService;
 class nsIIOService;
 class nsIURI;
 class imgIContainer;
 class imgIDecoderObserver;
 class imgIRequest;
 class imgILoader;
 class imgICache;
-class nsIPrefBranch;
+class nsIPrefBranch2;
 class nsIImageLoadingContent;
 class nsIDOMHTMLFormElement;
 class nsIDOMDocument;
 class nsIConsoleService;
 class nsIStringBundleService;
 class nsIStringBundle;
 class nsIContentPolicy;
 class nsILineBreaker;
 class nsIWordBreaker;
 class nsIJSRuntimeService;
 class nsIEventListenerManager;
 class nsIScriptContext;
 class nsIRunnable;
 class nsIInterfaceRequestor;
 template<class E> class nsCOMArray;
-class nsIPref;
 struct JSRuntime;
 class nsICaseConversion;
 class nsIUGenCategory;
 class nsIWidget;
 class nsIDragSession;
 class nsPIDOMWindow;
 class nsPIDOMEventTarget;
 class nsIPresShell;
 class nsIXPConnectJSObjectHolder;
+class nsPrefOldCallback;
 #ifdef MOZ_XTF
 class nsIXTFService;
 #endif
 #ifdef IBMBIDI
 class nsIBidiKeyboard;
 #endif
 class nsIMIMEHeaderParam;
 
+#ifndef have_PrefChangedFunc_typedef
+typedef int (*PR_CALLBACK PrefChangedFunc)(const char *, void *);
+#define have_PrefChangedFunc_typedef
+#endif
+
 extern const char kLoadAsData[];
 
 enum EventNameType {
   EventNameType_None = 0x0000,
   EventNameType_HTML = 0x0001,
   EventNameType_XUL = 0x0002,
   EventNameType_SVGGraphic = 0x0004, // svg graphic elements
   EventNameType_SVGSVG = 0x0008, // the svg element
@@ -554,17 +559,17 @@ public:
   static void RegisterPrefCallback(const char *aPref,
                                    PrefChangedFunc aCallback,
                                    void * aClosure);
   static void UnregisterPrefCallback(const char *aPref,
                                      PrefChangedFunc aCallback,
                                      void * aClosure);
   static void AddBoolPrefVarCache(const char* aPref, PRBool* aVariable);
   static void AddIntPrefVarCache(const char* aPref, PRInt32* aVariable);
-  static nsIPrefBranch *GetPrefBranch()
+  static nsIPrefBranch2 *GetPrefBranch()
   {
     return sPrefBranch;
   }
 
   static nsILineBreaker* LineBreaker()
   {
     return sLineBreaker;
   }
@@ -1532,19 +1537,19 @@ private:
   static nsINameSpaceManager *sNameSpaceManager;
 
   static nsIIOService *sIOService;
 
 #ifdef MOZ_XTF
   static nsIXTFService *sXTFService;
 #endif
 
-  static nsIPrefBranch *sPrefBranch;
-
-  static nsIPref *sPref;
+  static nsIPrefBranch2 *sPrefBranch;
+  // For old compatibility of RegisterPrefCallback
+  static nsCOMArray<nsPrefOldCallback> *sPrefCallbackList;
 
   static imgILoader* sImgLoader;
   static imgICache* sImgCache;
 
   static nsIConsoleService* sConsoleService;
 
   static nsDataHashtable<nsISupportsHashKey, EventNameMapping>* sEventTable;
 
--- a/content/base/public/nsIObjectLoadingContent.idl
+++ b/content/base/public/nsIObjectLoadingContent.idl
@@ -119,10 +119,11 @@ interface nsIObjectLoadingContent : nsIS
   /**
    * If this object is in going to be printed, this method
    * returns the nsIObjectFrame object which should be used when
    * printing the plugin. The returned nsIFrame is in the original document,
    * not in the static clone.
    */
   [noscript] nsIFrame getPrintFrame();
 
-  [noscript] void pluginCrashed();
+  [noscript] void pluginCrashed(in AString pluginName,
+                                in boolean submittedCrashReport);
 };
--- a/content/base/src/nsContentList.cpp
+++ b/content/base/src/nsContentList.cpp
@@ -291,16 +291,119 @@ NS_GetContentList(nsINode* aRootNode, ns
 
     gCachedContentList = list;
     NS_ADDREF(gCachedContentList);
   }
 
   return list;
 }
 
+// Hashtable for storing nsCacheableFuncStringContentList
+static PLDHashTable gFuncStringContentListHashTable;
+
+struct FuncStringContentListHashEntry : public PLDHashEntryHdr
+{
+  nsCacheableFuncStringContentList* mContentList;
+};
+
+static PLDHashNumber
+FuncStringContentListHashtableHashKey(PLDHashTable *table, const void *key)
+{
+  const nsFuncStringCacheKey* funcStringKey =
+    static_cast<const nsFuncStringCacheKey *>(key);
+  return funcStringKey->GetHash();
+}
+
+static PRBool
+FuncStringContentListHashtableMatchEntry(PLDHashTable *table,
+                               const PLDHashEntryHdr *entry,
+                               const void *key)
+{
+  const FuncStringContentListHashEntry *e =
+    static_cast<const FuncStringContentListHashEntry *>(entry);
+  const nsFuncStringCacheKey* ourKey =
+    static_cast<const nsFuncStringCacheKey *>(key);
+
+  return e->mContentList->Equals(ourKey);
+}
+
+already_AddRefed<nsContentList>
+NS_GetFuncStringContentList(nsINode* aRootNode,
+                            nsContentListMatchFunc aFunc,
+                            nsContentListDestroyFunc aDestroyFunc,
+                            void* aData,
+                            const nsAString& aString)
+{
+  NS_ASSERTION(aRootNode, "content list has to have a root");
+
+  nsCacheableFuncStringContentList* list = nsnull;
+
+  static PLDHashTableOps hash_table_ops =
+  {
+    PL_DHashAllocTable,
+    PL_DHashFreeTable,
+    FuncStringContentListHashtableHashKey,
+    FuncStringContentListHashtableMatchEntry,
+    PL_DHashMoveEntryStub,
+    PL_DHashClearEntryStub,
+    PL_DHashFinalizeStub
+  };
+
+  // Initialize the hashtable if needed.
+  if (!gFuncStringContentListHashTable.ops) {
+    PRBool success = PL_DHashTableInit(&gFuncStringContentListHashTable,
+                                       &hash_table_ops, nsnull,
+                                       sizeof(FuncStringContentListHashEntry),
+                                       16);
+
+    if (!success) {
+      gFuncStringContentListHashTable.ops = nsnull;
+    }
+  }
+
+  FuncStringContentListHashEntry *entry = nsnull;
+  // First we look in our hashtable.  Then we create a content list if needed
+  if (gFuncStringContentListHashTable.ops) {
+    nsFuncStringCacheKey hashKey(aRootNode, aFunc, aString);
+
+    // A PL_DHASH_ADD is equivalent to a PL_DHASH_LOOKUP for cases
+    // when the entry is already in the hashtable.
+    entry = static_cast<FuncStringContentListHashEntry *>
+                       (PL_DHashTableOperate(&gFuncStringContentListHashTable,
+                                             &hashKey,
+                                             PL_DHASH_ADD));
+    if (entry)
+      list = entry->mContentList;
+  }
+
+  if (!list) {
+    // We need to create a ContentList and add it to our new entry, if
+    // we have an entry
+    list = new nsCacheableFuncStringContentList(aRootNode, aFunc, aDestroyFunc, aData, aString);
+    if (entry) {
+      if (list)
+        entry->mContentList = list;
+      else
+        PL_DHashTableRawRemove(&gContentListHashTable, entry);
+    }
+
+    NS_ENSURE_TRUE(list, nsnull);
+  } else {
+    // List was already in the hashtable; clean up our new aData
+    if (aDestroyFunc) {
+      (*aDestroyFunc)(aData);
+    }
+  }
+
+  NS_ADDREF(list);
+
+  // Don't cache these lists globally
+
+  return list;
+}
 
 // nsContentList implementation
 
 nsContentList::nsContentList(nsINode* aRootNode,
                              nsIAtom* aMatchAtom,
                              PRInt32 aMatchNameSpaceId,
                              PRBool aDeep)
   : nsBaseContentList(),
@@ -445,17 +548,17 @@ nsContentList::IndexOf(nsIContent* aCont
   return IndexOf(aContent, PR_TRUE);
 }
 
 void
 nsContentList::NodeWillBeDestroyed(const nsINode* aNode)
 {
   // We shouldn't do anything useful from now on
 
-  RemoveFromHashtable();
+  RemoveFromCaches();
   mRootNode = nsnull;
 
   // We will get no more updates, so we can never know we're up to
   // date
   SetDirty();
 }
 
 // static
@@ -908,16 +1011,39 @@ nsContentList::BringSelfUpToDate(PRBool 
   if (mState != LIST_UP_TO_DATE)
     PopulateSelf(PRUint32(-1));
     
   ASSERT_IN_SYNC;
   NS_ASSERTION(!mRootNode || mState == LIST_UP_TO_DATE,
                "PopulateSelf dod not bring content list up to date!");
 }
 
+nsCacheableFuncStringContentList::~nsCacheableFuncStringContentList()
+{
+  RemoveFromFuncStringHashtable();
+}
+
+void
+nsCacheableFuncStringContentList::RemoveFromFuncStringHashtable()
+{
+  if (!gFuncStringContentListHashTable.ops) {
+    return;
+  }
+
+  nsFuncStringCacheKey key(mRootNode, mFunc, mString);
+  PL_DHashTableOperate(&gFuncStringContentListHashTable,
+                       &key,
+                       PL_DHASH_REMOVE);
+
+  if (gFuncStringContentListHashTable.entryCount == 0) {
+    PL_DHashTableFinish(&gFuncStringContentListHashTable);
+    gFuncStringContentListHashTable.ops = nsnull;
+  }
+}
+
 #ifdef DEBUG_CONTENT_LIST
 void
 nsContentList::AssertInSync()
 {
   if (mState == LIST_DIRTY) {
     return;
   }
 
--- a/content/base/src/nsContentList.h
+++ b/content/base/src/nsContentList.h
@@ -50,16 +50,17 @@
 #include "nsIHTMLCollection.h"
 #include "nsIDOMNodeList.h"
 #include "nsINodeList.h"
 #include "nsStubMutationObserver.h"
 #include "nsIAtom.h"
 #include "nsINameSpaceManager.h"
 #include "nsCycleCollectionParticipant.h"
 #include "nsWrapperCache.h"
+#include "nsCRT.h"
 
 // Magic namespace id that means "match all namespaces".  This is
 // negative so it won't collide with actual namespace constants.
 #define kNameSpaceID_Wildcard PR_INT32_MIN
 
 // This is a callback function type that can be used to implement an
 // arbitrary matching algorithm.  aContent is the content that may
 // match the list, while aNamespaceID, aAtom, and aData are whatever
@@ -392,16 +393,25 @@ protected:
    */
   void SetDirty()
   {
     mState = LIST_DIRTY;
     Reset();
   }
 
   /**
+   * To be called from non-destructor locations that want to remove from caches.
+   * Needed because if subclasses want to have cache behavior they can't just
+   * override RemoveFromHashtable(), since we call that in our destructor.
+   */
+  virtual void RemoveFromCaches() {
+    RemoveFromHashtable();
+  }
+
+  /**
    * Function to use to determine whether a piece of content matches
    * our criterion
    */
   nsContentListMatchFunc mFunc;
   /**
    * Cleanup closure data with this.
    */
   nsContentListDestroyFunc mDestroyFunc;
@@ -429,13 +439,74 @@ protected:
    */
   PRPackedBool mFuncMayDependOnAttr;
 
 #ifdef DEBUG_CONTENT_LIST
   void AssertInSync();
 #endif
 };
 
+/**
+ * A class of cacheable content list; cached on the combination of aRootNode + aFunc + aDataString
+ */
+class nsCacheableFuncStringContentList;
+
+class NS_STACK_CLASS nsFuncStringCacheKey {
+public:
+  nsFuncStringCacheKey(nsINode* aRootNode,
+                       nsContentListMatchFunc aFunc,
+                       const nsAString& aString) :
+    mRootNode(aRootNode),
+    mFunc(aFunc),
+    mString(aString)
+    {}
+
+  PRUint32 GetHash(void) const
+  {
+    return NS_PTR_TO_INT32(mRootNode) ^ (NS_PTR_TO_INT32(mFunc) << 12) ^
+      nsCRT::HashCode(PromiseFlatString(mString).get());
+  }
+
+private:
+  friend class nsCacheableFuncStringContentList;
+
+  nsINode* const mRootNode;
+  const nsContentListMatchFunc mFunc;
+  const nsAString& mString;
+};
+
+class nsCacheableFuncStringContentList : public nsContentList {
+public:
+  nsCacheableFuncStringContentList(nsINode* aRootNode,
+                                   nsContentListMatchFunc aFunc,
+                                   nsContentListDestroyFunc aDestroyFunc,
+                                   void* aData,
+                                   const nsAString& aString) :
+    nsContentList(aRootNode, aFunc, aDestroyFunc, aData),
+    mString(aString)
+  {}
+
+  virtual ~nsCacheableFuncStringContentList();
+
+  PRBool Equals(const nsFuncStringCacheKey* aKey) {
+    return mRootNode == aKey->mRootNode && mFunc == aKey->mFunc &&
+      mString == aKey->mString;
+  }
+protected:
+  virtual void RemoveFromCaches() {
+    RemoveFromFuncStringHashtable();
+  }
+  void RemoveFromFuncStringHashtable();
+
+  nsString mString;
+};
+
 already_AddRefed<nsContentList>
 NS_GetContentList(nsINode* aRootNode, nsIAtom* aMatchAtom,
                   PRInt32 aMatchNameSpaceId);
 
+already_AddRefed<nsContentList>
+NS_GetFuncStringContentList(nsINode* aRootNode,
+                            nsContentListMatchFunc aFunc,
+                            nsContentListDestroyFunc aDestroyFunc,
+                            void* aData,
+                            const nsAString& aString);
 #endif // nsContentList_h___
--- a/content/base/src/nsContentSink.cpp
+++ b/content/base/src/nsContentSink.cpp
@@ -185,25 +185,25 @@ NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN(
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NATIVE_MEMBER(mNodeInfoManager,
                                                   nsNodeInfoManager)
 NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
 
 
 nsContentSink::nsContentSink()
 {
   // We have a zeroing operator new
-  NS_ASSERTION(mLayoutStarted == PR_FALSE, "What?");
-  NS_ASSERTION(mDynamicLowerValue == PR_FALSE, "What?");
-  NS_ASSERTION(mParsing == PR_FALSE, "What?");
+  NS_ASSERTION(!mLayoutStarted, "What?");
+  NS_ASSERTION(!mDynamicLowerValue, "What?");
+  NS_ASSERTION(!mParsing, "What?");
   NS_ASSERTION(mLastSampledUserEventTime == 0, "What?");
   NS_ASSERTION(mDeflectedCount == 0, "What?");
-  NS_ASSERTION(mDroppedTimer == PR_FALSE, "What?");
+  NS_ASSERTION(!mDroppedTimer, "What?");
   NS_ASSERTION(mInMonolithicContainer == 0, "What?");
   NS_ASSERTION(mInNotification == 0, "What?");
-  NS_ASSERTION(mDeferredLayoutStart == PR_FALSE, "What?");
+  NS_ASSERTION(!mDeferredLayoutStart, "What?");
 
 #ifdef NS_DEBUG
   if (!gContentSinkLogModuleInfo) {
     gContentSinkLogModuleInfo = PR_NewLogModule("nscontentsink");
   }
 #endif
 }
 
--- a/content/base/src/nsContentUtils.cpp
+++ b/content/base/src/nsContentUtils.cpp
@@ -43,17 +43,17 @@
 /* A namespace class for static layout utilities. */
 
 #include "nsJSUtils.h"
 #include "nsCOMPtr.h"
 #include "nsAString.h"
 #include "nsPrintfCString.h"
 #include "nsUnicharUtils.h"
 #include "nsIPrefService.h"
-#include "nsIPrefBranch.h"
+#include "nsIPrefBranch2.h"
 #include "nsIPrefLocalizedString.h"
 #include "nsServiceManagerUtils.h"
 #include "nsIScriptGlobalObject.h"
 #include "nsIScriptContext.h"
 #include "nsIDOMScriptObjectFactory.h"
 #include "nsDOMCID.h"
 #include "nsContentUtils.h"
 #include "nsIXPConnect.h"
@@ -193,18 +193,17 @@ nsIXPConnect *nsContentUtils::sXPConnect
 nsIScriptSecurityManager *nsContentUtils::sSecurityManager;
 nsIThreadJSContextStack *nsContentUtils::sThreadJSContextStack;
 nsIParserService *nsContentUtils::sParserService = nsnull;
 nsINameSpaceManager *nsContentUtils::sNameSpaceManager;
 nsIIOService *nsContentUtils::sIOService;
 #ifdef MOZ_XTF
 nsIXTFService *nsContentUtils::sXTFService = nsnull;
 #endif
-nsIPrefBranch *nsContentUtils::sPrefBranch = nsnull;
-nsIPref *nsContentUtils::sPref = nsnull;
+nsIPrefBranch2 *nsContentUtils::sPrefBranch = nsnull;
 imgILoader *nsContentUtils::sImgLoader;
 imgICache *nsContentUtils::sImgCache;
 nsIConsoleService *nsContentUtils::sConsoleService;
 nsDataHashtable<nsISupportsHashKey, EventNameMapping>* nsContentUtils::sEventTable = nsnull;
 nsIStringBundleService *nsContentUtils::sStringBundleService;
 nsIStringBundle *nsContentUtils::sStringBundles[PropertiesFile_COUNT];
 nsIContentPolicy *nsContentUtils::sContentPolicyService;
 PRBool nsContentUtils::sTriedToGetContentPolicy = PR_FALSE;
@@ -226,16 +225,18 @@ PRUint32 nsContentUtils::sRunnersCountAt
 PRUint32 nsContentUtils::sScriptBlockerCountWhereRunnersPrevented = 0;
 nsIInterfaceRequestor* nsContentUtils::sSameOriginChecker = nsnull;
 
 nsIJSRuntimeService *nsAutoGCRoot::sJSRuntimeService;
 JSRuntime *nsAutoGCRoot::sJSScriptRuntime;
 
 PRBool nsContentUtils::sInitialized = PR_FALSE;
 
+nsCOMArray<nsPrefOldCallback> *nsContentUtils::sPrefCallbackList = nsnull;
+
 static PLDHashTable sEventListenerManagersHash;
 
 class EventListenerManagerMapEntry : public PLDHashEntryHdr
 {
 public:
   EventListenerManagerMapEntry(const void *aKey)
     : mKey(aKey)
   {
@@ -275,16 +276,53 @@ EventListenerManagerHashClearEntry(PLDHa
 class nsSameOriginChecker : public nsIChannelEventSink,
                             public nsIInterfaceRequestor
 {
   NS_DECL_ISUPPORTS
   NS_DECL_NSICHANNELEVENTSINK
   NS_DECL_NSIINTERFACEREQUESTOR
 };
 
+// For nsContentUtils::RegisterPrefCallback/UnregisterPrefCallback
+class nsPrefOldCallback : public nsIObserver
+{
+public:
+  NS_DECL_ISUPPORTS
+  NS_DECL_NSIOBSERVER
+
+public:
+  nsPrefOldCallback(const char *aPref, PrefChangedFunc aCallback, void *aClosure) : mPref(aPref), mCallback(aCallback), mClosure(aClosure) {
+  }
+
+  PRBool IsEqual(const char *aPref, PrefChangedFunc aCallback, void *aClosure) {
+    return aCallback == mCallback &&
+           aClosure == mClosure &&
+           mPref.Equals(aPref);
+  }
+
+public:
+  nsCString       mPref;
+  PrefChangedFunc mCallback;
+  void            *mClosure;
+};
+
+NS_IMPL_ISUPPORTS1(nsPrefOldCallback, nsIObserver)
+
+NS_IMETHODIMP
+nsPrefOldCallback::Observe(nsISupports   *aSubject,
+                         const char      *aTopic,
+                         const PRUnichar *aData)
+{
+  NS_ASSERTION(!strcmp(aTopic, NS_PREFBRANCH_PREFCHANGE_TOPIC_ID),
+               "invalid topic");
+  mCallback(NS_LossyConvertUTF16toASCII(aData).get(), mClosure);
+
+  return NS_OK;
+}
+
 // static
 nsresult
 nsContentUtils::Init()
 {
   if (sInitialized) {
     NS_WARNING("Init() called twice");
 
     return NS_OK;
@@ -292,19 +330,16 @@ nsContentUtils::Init()
 
   nsresult rv = CallGetService(NS_SCRIPTSECURITYMANAGER_CONTRACTID,
                                &sSecurityManager);
   NS_ENSURE_SUCCESS(rv, rv);
 
   // It's ok to not have a pref service.
   CallGetService(NS_PREFSERVICE_CONTRACTID, &sPrefBranch);
 
-  // It's ok to not have prefs too.
-  CallGetService(NS_PREF_CONTRACTID, &sPref);
-
   rv = NS_GetNameSpaceManager(&sNameSpaceManager);
   NS_ENSURE_SUCCESS(rv, rv);
 
   rv = CallGetService(nsIXPConnect::GetCID(), &sXPConnect);
   NS_ENSURE_SUCCESS(rv, rv);
 
   rv = CallGetService(kJSStackContractID, &sThreadJSContextStack);
   NS_ENSURE_SUCCESS(rv, rv);
@@ -881,16 +916,30 @@ nsContentUtils::Shutdown()
   NS_HTMLParanoidFragmentSinkShutdown();
   NS_XHTMLParanoidFragmentSinkShutdown();
 
   NS_IF_RELEASE(sContentPolicyService);
   sTriedToGetContentPolicy = PR_FALSE;
   PRUint32 i;
   for (i = 0; i < PropertiesFile_COUNT; ++i)
     NS_IF_RELEASE(sStringBundles[i]);
+
+  // Clean up c-style's observer 
+  if (sPrefCallbackList) {
+    while (sPrefCallbackList->Count() > 0) {
+      nsCOMPtr<nsPrefOldCallback> callback = (*sPrefCallbackList)[0];
+      NS_ABORT_IF_FALSE(callback, "Invalid c-style callback is appended");
+      if (sPrefBranch)
+        sPrefBranch->RemoveObserver(callback->mPref.get(), callback);
+      sPrefCallbackList->RemoveObject(callback);
+    }
+    delete sPrefCallbackList;
+    sPrefCallbackList = nsnull;
+  }
+
   NS_IF_RELEASE(sStringBundleService);
   NS_IF_RELEASE(sConsoleService);
   NS_IF_RELEASE(sDOMScriptObjectFactory);
   if (sJSGCThingRootCount == 0 && sXPConnect)
     NS_RELEASE(sXPConnect);
   NS_IF_RELEASE(sSecurityManager);
   NS_IF_RELEASE(sThreadJSContextStack);
   NS_IF_RELEASE(sNameSpaceManager);
@@ -901,17 +950,16 @@ nsContentUtils::Shutdown()
   NS_IF_RELEASE(sCaseConv);
   NS_IF_RELEASE(sGenCat);
 #ifdef MOZ_XTF
   NS_IF_RELEASE(sXTFService);
 #endif
   NS_IF_RELEASE(sImgLoader);
   NS_IF_RELEASE(sImgCache);
   NS_IF_RELEASE(sPrefBranch);
-  NS_IF_RELEASE(sPref);
 #ifdef IBMBIDI
   NS_IF_RELEASE(sBidiKeyboard);
 #endif
 
   delete sEventTable;
   sEventTable = nsnull;
 
   if (sPtrsToPtrsToRelease) {
@@ -2573,34 +2621,64 @@ nsContentUtils::GetStringPref(const char
     if (theString) {
       theString->ToString(getter_Copies(result));
     }
   }
 
   return result;
 }
 
+// RegisterPrefCallback/UnregisterPrefCallback are backward compatiblity for
+// c-style observer.
+
 // static
 void
 nsContentUtils::RegisterPrefCallback(const char *aPref,
                                      PrefChangedFunc aCallback,
                                      void * aClosure)
 {
-  if (sPref)
-    sPref->RegisterCallback(aPref, aCallback, aClosure);
+  if (sPrefBranch) {
+    if (!sPrefCallbackList) {
+      sPrefCallbackList = new nsCOMArray<nsPrefOldCallback> ();
+      if (!sPrefCallbackList)
+        return;
+    }
+
+    nsPrefOldCallback *callback = new nsPrefOldCallback(aPref, aCallback, aClosure);
+    if (callback) {
+      if (NS_SUCCEEDED(sPrefBranch->AddObserver(aPref, callback, PR_FALSE))) {
+        sPrefCallbackList->AppendObject(callback);
+        return;
+      }
+      // error to get/add nsIPrefBranch2.  Destroy callback information
+      delete callback;
+    }
+  }
 }
 
 // static
 void
 nsContentUtils::UnregisterPrefCallback(const char *aPref,
                                        PrefChangedFunc aCallback,
                                        void * aClosure)
 {
-  if (sPref)
-    sPref->UnregisterCallback(aPref, aCallback, aClosure);
+  if (sPrefBranch) {
+    if (!sPrefCallbackList)
+      return;
+
+    int i;
+    for (i = 0; i < sPrefCallbackList->Count(); i++) {
+      nsCOMPtr<nsPrefOldCallback> callback = (*sPrefCallbackList)[i];
+      if (callback && callback->IsEqual(aPref, aCallback, aClosure)) {
+        sPrefBranch->RemoveObserver(aPref, callback);
+        sPrefCallbackList->RemoveObject(callback);
+        return;
+      }
+    }
+  }
 }
 
 static int
 BoolVarChanged(const char *aPref, void *aClosure)
 {
   PRBool* cache = static_cast<PRBool*>(aClosure);
   *cache = nsContentUtils::GetBoolPref(aPref, PR_FALSE);
   
--- a/content/base/src/nsDocument.cpp
+++ b/content/base/src/nsDocument.cpp
@@ -1793,16 +1793,17 @@ NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN(
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mChannel)
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR_AMBIGUOUS(mStyleAttrStyleSheet, nsIStyleSheet)
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mScriptEventManager)
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mXPathEvaluatorTearoff)
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mLayoutHistoryState)
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mOnloadBlocker)
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mFirstBaseNodeWithHref)
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mDOMImplementation)
+  NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mOriginalDocument)
 
   // An element will only be in the linkmap as long as it's in the
   // document, so we'll traverse the table here instead of from the element.
   if (tmp->mLinkMap.IsInitialized()) {
     tmp->mLinkMap.EnumerateEntries(LinkMapTraverser, &cb);
   }
 
   // Traverse all our nsCOMArrays.
@@ -1846,16 +1847,17 @@ NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN(ns
     tmp->mChildren.ChildAt(indx)->UnbindFromTree();
     tmp->mChildren.RemoveChildAt(indx);
   }
 
   NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mCachedRootContent)
   NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mDisplayDocument)
   NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mFirstBaseNodeWithHref)
   NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mDOMImplementation)
+  NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mOriginalDocument)
 
   NS_IMPL_CYCLE_COLLECTION_UNLINK_USERDATA
 
   tmp->mParentDocument = nsnull;
 
   NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMARRAY(mPreloadingImages)
 
   // nsDocument has a pretty complex destructor, so we're going to
@@ -2854,31 +2856,34 @@ nsDocument::GetElementsByClassNameHelper
   }
 
   nsBaseContentList* elements;
   if (info->mClasses.Count() > 0) {
     info->mCaseTreatment =
       aRootNode->GetOwnerDoc()->GetCompatibilityMode() ==
         eCompatibility_NavQuirks ?
           eIgnoreCase : eCaseMatters;
-  
-    elements = new nsContentList(aRootNode, MatchClassNames,
-                                 DestroyClassNameArray, info);
+
+    elements =
+      NS_GetFuncStringContentList(aRootNode, MatchClassNames,
+                                  DestroyClassNameArray, info,
+                                  aClasses).get();
   } else {
     delete info;
     info = nsnull;
     elements = new nsBaseContentList();
+    NS_IF_ADDREF(elements);
   }
   if (!elements) {
     delete info;
     return NS_ERROR_OUT_OF_MEMORY;
   }
 
+  // Transfer ownership
   *aReturn = elements;
-  NS_ADDREF(*aReturn);
 
   return NS_OK;
 }
 
 // static
 PRBool
 nsDocument::MatchClassNames(nsIContent* aContent,
                             PRInt32 aNamespaceID,
--- a/content/base/src/nsObjectLoadingContent.cpp
+++ b/content/base/src/nsObjectLoadingContent.cpp
@@ -39,26 +39,31 @@
 /*
  * A base class implementing nsIObjectLoadingContent for use by
  * various content nodes that want to provide plugin/document/image
  * loading functionality (eg <embed>, <object>, <applet>, etc).
  */
 
 // Interface headers
 #include "imgILoader.h"
+#include "nsEventDispatcher.h"
 #include "nsIContent.h"
 #include "nsIDocShell.h"
 #include "nsIDocument.h"
+#include "nsIDOMDataContainerEvent.h"
+#include "nsIDOMDocumentEvent.h"
+#include "nsIDOMEventTarget.h"
 #include "nsIExternalProtocolHandler.h"
 #include "nsIEventStateManager.h"
 #include "nsIObjectFrame.h"
 #include "nsIPluginDocument.h"
 #include "nsIPluginHost.h"
 #include "nsIPluginInstance.h"
 #include "nsIPresShell.h"
+#include "nsIPrivateDOMEvent.h"
 #include "nsIScriptGlobalObject.h"
 #include "nsIScriptSecurityManager.h"
 #include "nsIStreamConverterService.h"
 #include "nsIURILoader.h"
 #include "nsIURL.h"
 #include "nsIWebNavigation.h"
 #include "nsIWebNavigationInfo.h"
 #include "nsIScriptChannel.h"
@@ -74,16 +79,17 @@
 #include "nsContentPolicyUtils.h"
 #include "nsContentUtils.h"
 #include "nsDocShellCID.h"
 #include "nsGkAtoms.h"
 #include "nsThreadUtils.h"
 #include "nsNetUtil.h"
 #include "nsMimeTypes.h"
 #include "nsStyleUtil.h"
+#include "nsGUIEvent.h"
 
 // Concrete classes
 #include "nsFrameLoader.h"
 
 #include "nsObjectLoadingContent.h"
 #include "mozAutoDocUpdate.h"
 
 #ifdef PR_LOGGING
@@ -195,28 +201,98 @@ nsPluginErrorEvent::Run()
       type = NS_LITERAL_STRING("PluginDisabled");
       break;
     case ePluginBlocklisted:
       type = NS_LITERAL_STRING("PluginBlocklisted");
       break;
     case ePluginOutdated:
       type = NS_LITERAL_STRING("PluginOutdated");
       break;
-    case ePluginCrashed:
-      type = NS_LITERAL_STRING("PluginCrashed");
-      break;
     default:
       return NS_OK;
   }
   nsContentUtils::DispatchTrustedEvent(mContent->GetDocument(), mContent,
                                        type, PR_TRUE, PR_TRUE);
 
   return NS_OK;
 }
 
+/**
+ * A task for firing PluginCrashed DOM Events.
+ */
+class nsPluginCrashedEvent : public nsRunnable {
+public:
+  nsCOMPtr<nsIContent> mContent;
+  nsString mPluginName;
+  PRBool mSubmittedCrashReport;
+
+  nsPluginCrashedEvent(nsIContent* aContent,
+                       const nsAString& aPluginName,
+                       PRBool submittedCrashReport)
+    : mContent(aContent),
+      mPluginName(aPluginName),
+      mSubmittedCrashReport(submittedCrashReport)
+  {}
+
+  ~nsPluginCrashedEvent() {}
+
+  NS_IMETHOD Run();
+};
+
+NS_IMETHODIMP
+nsPluginCrashedEvent::Run()
+{
+  LOG(("OBJLC []: Firing plugin crashed event for content %p\n",
+       mContent.get()));
+
+  nsCOMPtr<nsIDOMDocumentEvent> domEventDoc =
+    do_QueryInterface(mContent->GetDocument());
+  if (!domEventDoc) {
+    NS_WARNING("Couldn't get document for PluginCrashed event!");
+    return NS_OK;
+  }
+
+  nsCOMPtr<nsIDOMEvent> event;
+  domEventDoc->CreateEvent(NS_LITERAL_STRING("datacontainerevents"),
+                           getter_AddRefs(event));
+  nsCOMPtr<nsIPrivateDOMEvent> privateEvent(do_QueryInterface(event));
+  nsCOMPtr<nsIDOMDataContainerEvent> containerEvent(do_QueryInterface(event));
+  if (!privateEvent || !containerEvent) {
+    NS_WARNING("Couldn't QI event for PluginCrashed event!");
+    return NS_OK;
+  }
+
+  event->InitEvent(NS_LITERAL_STRING("PluginCrashed"), PR_TRUE, PR_TRUE);
+  privateEvent->SetTrusted(PR_TRUE);
+  privateEvent->GetInternalNSEvent()->flags |= NS_EVENT_FLAG_ONLY_CHROME_DISPATCH;
+  
+  nsCOMPtr<nsIWritableVariant> variant;
+
+  // add a "pluginName" property to this event
+  variant = do_CreateInstance("@mozilla.org/variant;1");
+  if (!variant) {
+    NS_WARNING("Couldn't create pluginName variant for PluginCrashed event!");
+    return NS_OK;
+  }
+  variant->SetAsAString(mPluginName);
+  containerEvent->SetData(NS_LITERAL_STRING("pluginName"), variant);
+
+  // add a "submittedCrashReport" property to this event
+  variant = do_CreateInstance("@mozilla.org/variant;1");
+  if (!variant) {
+    NS_WARNING("Couldn't create crashSubmit variant for PluginCrashed event!");
+    return NS_OK;
+  }
+  variant->SetAsBool(mSubmittedCrashReport);
+  containerEvent->SetData(NS_LITERAL_STRING("submittedCrashReport"), variant);
+
+  nsEventDispatcher::DispatchDOMEvent(mContent, nsnull, event, nsnull, nsnull);
+  return NS_OK;
+}
+
 class AutoNotifier {
   public:
     AutoNotifier(nsObjectLoadingContent* aContent, PRBool aNotify) :
       mContent(aContent), mNotify(aNotify) {
         mOldType = aContent->Type();
         mOldState = aContent->ObjectState();
     }
     ~AutoNotifier() {
@@ -950,16 +1026,19 @@ nsObjectLoadingContent::ObjectState() co
       PRInt32 state = NS_EVENT_STATE_BROKEN;
       switch (mFallbackReason) {
         case ePluginDisabled:
           state |= NS_EVENT_STATE_HANDLER_DISABLED;
           break;
         case ePluginBlocklisted:
           state |= NS_EVENT_STATE_HANDLER_BLOCKED;
           break;
+        case ePluginCrashed:
+          state |= NS_EVENT_STATE_HANDLER_CRASHED;
+          break;
         case ePluginUnsupported:
           state |= NS_EVENT_STATE_TYPE_UNSUPPORTED;
           break;
       }
       return state;
   };
   NS_NOTREACHED("unknown type?");
   // this return statement only exists to avoid a compile warning
@@ -1924,16 +2003,24 @@ nsObjectLoadingContent::SetAbsoluteScree
   nsIObjectFrame* frame = GetExistingFrame(eFlushLayout);
   if (!frame)
     return NS_ERROR_NOT_AVAILABLE;
 
   return frame->SetAbsoluteScreenPosition(element, position, clip);
 }
 
 NS_IMETHODIMP
-nsObjectLoadingContent::PluginCrashed()
+nsObjectLoadingContent::PluginCrashed(const nsAString& pluginName,
+                                      PRBool submittedCrashReport)
 {
+  AutoNotifier notifier(this, PR_TRUE);
   UnloadContent();
   mFallbackReason = ePluginCrashed;
   nsCOMPtr<nsIContent> thisContent = do_QueryInterface(static_cast<nsIImageLoadingContent*>(this));
-  FirePluginError(thisContent, mFallbackReason);
+  nsCOMPtr<nsIRunnable> ev = new nsPluginCrashedEvent(thisContent,
+                                                      pluginName,
+                                                      submittedCrashReport);
+  nsresult rv = NS_DispatchToCurrentThread(ev);
+  if (NS_FAILED(rv)) {
+    NS_WARNING("failed to dispatch nsPluginCrashedEvent");
+  }
   return NS_OK;
 }
--- a/content/canvas/src/Makefile.in
+++ b/content/canvas/src/Makefile.in
@@ -54,26 +54,25 @@ CPPSRCS	= \
 	CanvasUtils.cpp \
 	nsCanvasRenderingContext2D.cpp \
 	$(NULL)
 
 # Canvas 3D Pieces
 
 ifdef MOZ_WEBGL
 
-ifeq (1_1,$(MOZ_X11)_$(NS_OSSO))
+ifdef MOZ_X11
+ifdef MOZ_PLATFORM_MAEMO
 WEBGL_PLATFORM = EGL
 DEFINES += -DUSE_GLES2
-endif
-
-ifeq (1_,$(MOZ_X11)_$(NS_OSSO))
+else
 WEBGL_PLATFORM = GLX
 EXTRA_DSO_LIBS += X11
 endif
-
+endif
 
 ifeq (windows,$(MOZ_WIDGET_TOOLKIT))
 ifdef WINCE
 WEBGL_PLATFORM = EGL
 DEFINES += -DUSE_GLES2
 else
 WEBGL_PLATFORM = WGL
 endif
--- a/content/canvas/src/nsGLPbufferEGL.cpp
+++ b/content/canvas/src/nsGLPbufferEGL.cpp
@@ -158,17 +158,17 @@ nsGLPbufferEGL::nsGLPbufferEGL()
 #define GLES2_LIB "/usr/lib/libGLESv2.so"
 #endif
 
 PRBool
 nsGLPbufferEGL::Init(mozilla::WebGLContext *priv)
 {
     mPriv = priv;
 
-#ifdef NS_OSSO
+#ifdef MOZ_PLATFORM_MAEMO
     // Maemo has missing DSO dependencies on their OpenGL libraries;
     // so ensure that the prerequisite libs are loaded in the process
     // before loading GL.  An alternate approach is to use LD_PRELOAD.
 
     // We'll just leak these libs; pvr_um.so seems to have been
     // present on an older OS image, and now pvr2d.so is used.
     PRLibSpec lspec;
     lspec.type = PR_LibSpec_Pathname;
@@ -194,17 +194,17 @@ nsGLPbufferEGL::Init(mozilla::WebGLConte
 
     if (!gEGLWrap.fInitialize(mDisplay, NULL, NULL)) {
         LogMessage("egl init failed");
         return PR_FALSE;
     }
 
     gEGLWrap.fBindAPI (EGL_OPENGL_ES_API);
 
-#if defined(MOZ_X11) && defined(NS_OSSO)
+#if defined(MOZ_X11) && defined(MOZ_PLATFORM_MAEMO)
     EGLint attribs[] = {
         EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT,
         EGL_SURFACE_TYPE, EGL_PIXMAP_BIT,
         EGL_RED_SIZE, 3,
         EGL_GREEN_SIZE, 3,
         EGL_BLUE_SIZE, 3,
         EGL_ALPHA_SIZE, 3,
         EGL_DEPTH_SIZE, 1,
@@ -472,16 +472,16 @@ nsGLPbufferEGL::SwapBuffers()
     unsigned char *src = mThebesSurface->Data();
     Premultiply(src, len);
 #endif
 }
 
 gfxASurface*
 nsGLPbufferEGL::ThebesSurface()
 {
-#if defined(MOZ_X11) && defined(NS_OSSO)
+#if defined(MOZ_X11) && defined(MOZ_PLATFORM_MAEMO)
     if (getenv("IMAGE"))
         return mThebesSurface;
     return mXlibSurface;
 #elif defined(WINCE)
     return mThebesSurface;
 #endif
 }
--- a/content/events/public/nsIEventStateManager.h
+++ b/content/events/public/nsIEventStateManager.h
@@ -192,9 +192,13 @@ NS_DEFINE_STATIC_IID_ACCESSOR(nsIEventSt
 #define NS_EVENT_STATE_HANDLER_BLOCKED \
                                      0x01000000
 // Handler for the content has been disabled
 #define NS_EVENT_STATE_HANDLER_DISABLED \
                                      0x02000000
 
 #define NS_EVENT_STATE_INDETERMINATE 0x04000000 // CSS3-Selectors
 
+// Handler for the content has crashed
+#define NS_EVENT_STATE_HANDLER_CRASHED \
+                                     0x08000000
+
 #endif // nsIEventStateManager_h__
--- a/content/events/src/nsEventStateManager.cpp
+++ b/content/events/src/nsEventStateManager.cpp
@@ -782,18 +782,17 @@ nsEventStateManager::Init()
 {
   nsresult rv;
   nsCOMPtr<nsIObserverService> observerService =
            do_GetService("@mozilla.org/observer-service;1", &rv);
   NS_ENSURE_SUCCESS(rv, rv);
 
   observerService->AddObserver(this, NS_XPCOM_SHUTDOWN_OBSERVER_ID, PR_TRUE);
 
-  nsCOMPtr<nsIPrefBranch2> prefBranch =
-    do_QueryInterface(nsContentUtils::GetPrefBranch());
+  nsIPrefBranch2* prefBranch = nsContentUtils::GetPrefBranch();
 
   if (prefBranch) {
     if (sESMInstanceCount == 1) {
       sLeftClickOnly =
         nsContentUtils::GetBoolPref("nglayout.events.dispatchLeftClickOnly",
                                     sLeftClickOnly);
 
       sChromeAccessModifier =
@@ -862,18 +861,17 @@ nsEventStateManager::~nsEventStateManage
     }
   }
 
 }
 
 nsresult
 nsEventStateManager::Shutdown()
 {
-  nsCOMPtr<nsIPrefBranch2> prefBranch =
-    do_QueryInterface(nsContentUtils::GetPrefBranch());
+  nsIPrefBranch2* prefBranch = nsContentUtils::GetPrefBranch();
 
   if (prefBranch) {
     prefBranch->RemoveObserver("accessibility.accesskeycausesactivation", this);
     prefBranch->RemoveObserver("nglayout.events.dispatchLeftClickOnly", this);
     prefBranch->RemoveObserver("ui.key.generalAccessKey", this);
     prefBranch->RemoveObserver("ui.key.chromeAccess", this);
     prefBranch->RemoveObserver("ui.key.contentAccess", this);
 #if 0
--- a/content/events/src/nsEventStateManager.h
+++ b/content/events/src/nsEventStateManager.h
@@ -58,19 +58,19 @@
 class nsIPresShell;
 class nsIDocShell;
 class nsIDocShellTreeNode;
 class nsIDocShellTreeItem;
 class imgIContainer;
 class nsDOMDataTransfer;
 
 // mac uses click-hold context menus, a holdover from 4.x
-// touch screens (like hildon) could use this also, 
+// touch screens (like maemo) could use this also, 
 // perhaps we should move to NS_TOUCHSCREEN
-#if defined(XP_MACOSX) || defined(MOZ_PLATFORM_HILDON)
+#if defined(XP_MACOSX) || defined(MOZ_PLATFORM_MAEMO)
 #define CLICK_HOLD_CONTEXT_MENUS 1
 #endif
 
 
 /*
  * Event listener manager
  */
 
--- a/content/events/src/nsXMLEventsManager.cpp
+++ b/content/events/src/nsXMLEventsManager.cpp
@@ -316,17 +316,17 @@ PRBool nsXMLEventsManager::RemoveListene
 }
 
 void nsXMLEventsManager::AddListeners(nsIDocument* aDocument)
 {
   nsIContent *cur;
   for (int i = 0; i < mIncomplete.Count(); ++i) {
     cur = mIncomplete[i];
     //If this succeeds, the object will be removed from mIncomplete
-    if (nsXMLEventsListener::InitXMLEventsListener(aDocument, this, cur) == PR_TRUE)
+    if (nsXMLEventsListener::InitXMLEventsListener(aDocument, this, cur))
       --i;
   }
 }
 
 void 
 nsXMLEventsManager::BeginUpdate(nsIDocument* aDocument, nsUpdateType aUpdateType) {}
 void 
 nsXMLEventsManager::EndUpdate(nsIDocument* aDocument, nsUpdateType aUpdateType) {}
--- a/content/html/content/src/nsHTMLInputElement.cpp
+++ b/content/html/content/src/nsHTMLInputElement.cpp
@@ -55,18 +55,16 @@
 #include "nsGenericHTMLElement.h"
 #include "nsGkAtoms.h"
 #include "nsStyleConsts.h"
 #include "nsPresContext.h"
 #include "nsMappedAttributes.h"
 #include "nsIFormControl.h"
 #include "nsIForm.h"
 #include "nsIFormSubmission.h"
-#include "nsITextControlFrame.h"
-#include "nsIRadioControlFrame.h"
 #include "nsIDocument.h"
 #include "nsIPresShell.h"
 #include "nsIFormControlFrame.h"
 #include "nsITextControlFrame.h"
 #include "nsIFrame.h"
 #include "nsIEventStateManager.h"
 #include "nsIServiceManager.h"
 #include "nsIScriptSecurityManager.h"
@@ -76,34 +74,32 @@
 #include "nsGUIEvent.h"
 
 #include "nsPresState.h"
 #include "nsLayoutErrors.h"
 #include "nsIDOMEvent.h"
 #include "nsIDOMNSEvent.h"
 #include "nsIDOMNodeList.h"
 #include "nsIDOMHTMLCollection.h"
-#include "nsICheckboxControlFrame.h"
 #include "nsLinebreakConverter.h" //to strip out carriage returns
 #include "nsReadableUtils.h"
 #include "nsUnicharUtils.h"
 #include "nsEventDispatcher.h"
 #include "nsLayoutUtils.h"
 #include "nsWidgetsCID.h"
 #include "nsILookAndFeel.h"
 
 #include "nsIDOMMutationEvent.h"
 #include "nsIDOMEventTarget.h"
 #include "nsMutationEvent.h"
 #include "nsIEventListenerManager.h"
 
 #include "nsRuleData.h"
 
 // input type=radio
-#include "nsIRadioControlFrame.h"
 #include "nsIRadioGroupContainer.h"
 
 // input type=file
 #include "nsIMIMEService.h"
 #include "nsCExternalHandlerService.h"
 #include "nsIFile.h"
 #include "nsILocalFile.h"
 #include "nsIFileStreams.h"
@@ -1363,30 +1359,20 @@ nsHTMLInputElement::SetCheckedInternal(P
   //
   // Set the value
   //
   SET_BOOLBIT(mBitField, BF_CHECKED, aChecked);
 
   //
   // Notify the frame
   //
-  nsIFrame* frame = GetPrimaryFrame();
-  if (frame) {
-    nsPresContext *presContext = GetPresContext();
-
-    if (mType == NS_FORM_INPUT_CHECKBOX) {
-      nsICheckboxControlFrame* checkboxFrame = do_QueryFrame(frame);
-      if (checkboxFrame) {
-        checkboxFrame->OnChecked(presContext, aChecked);
-      }
-    } else if (mType == NS_FORM_INPUT_RADIO) {
-      nsIRadioControlFrame* radioFrame = do_QueryFrame(frame);
-      if (radioFrame) {
-        radioFrame->OnChecked(presContext, aChecked);
-      }
+  if (mType == NS_FORM_INPUT_CHECKBOX || mType == NS_FORM_INPUT_RADIO) {
+    nsIFrame* frame = GetPrimaryFrame();
+    if (frame) {
+      frame->InvalidateOverflowRect();
     }
   }
 
   // Notify the document that the CSS :checked pseudoclass for this element
   // has changed state.
   if (aNotify) {
     nsIDocument* document = GetCurrentDoc();
     if (document) {
--- a/content/html/content/src/nsHTMLTextAreaElement.cpp
+++ b/content/html/content/src/nsHTMLTextAreaElement.cpp
@@ -794,16 +794,19 @@ nsHTMLTextAreaElement::SetSelectionRange
 
 nsresult
 nsHTMLTextAreaElement::Reset()
 {
   nsresult rv;
   // If the frame is there, we have to set the value so that it will show up.
   nsIFormControlFrame* formControlFrame = GetFormControlFrame(PR_FALSE);
   if (formControlFrame) {
+    // To get the initial spellchecking, reset value to
+    // empty string before setting the default value.
+    SetValue(EmptyString());
     nsAutoString resetVal;
     GetDefaultValue(resetVal);
     rv = SetValue(resetVal);
     NS_ENSURE_SUCCESS(rv, rv);
   }
   SetValueChanged(PR_FALSE);
   return NS_OK;
 }
--- a/content/html/content/test/Makefile.in
+++ b/content/html/content/test/Makefile.in
@@ -135,16 +135,17 @@ include $(topsrcdir)/config/rules.mk
 		test_bug347174_xsl.html \
 		test_bug347174_xslp.html \
 		347174transformable.xml \
 		347174transform.xsl \
 		test_bug481335.xhtml \
 		test_bug500885.html \
 		test_bug514856.html \
 		bug514856_iframe.html \
+		test_bug518122.html \
 		test_bug519987.html \
 		test_bug523771.html \
 		form_submit_server.sjs \
 		test_bug529819.html \
 		test_bug529859.html \
 		test_bug535043.html \
 		$(NULL)
 
new file mode 100644
--- /dev/null
+++ b/content/html/content/test/test_bug518122.html
@@ -0,0 +1,122 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=518122
+-->
+<head>
+  <title>Test for Bug 518122</title>
+  <script type="application/javascript" src="/MochiKit/packed.js"></script>
+  <script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+  <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+</head>
+<body onload="runTests()">
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=518122">Mozilla Bug 518122</a>
+<p id="display"></p>
+<div id="content" style="display: none">
+  
+</div>
+<pre id="test">
+<script type="application/javascript">
+
+/** Test for Bug 518122 **/
+
+SimpleTest.waitForExplicitFinish();
+
+var simple_tests = [ ["foo", "foo"],
+                     ["", ""],
+                     [null, ""],
+                     [undefined , "undefined"],
+                     ["\n", "\n"],
+                     ["\r", "\n"],
+                     ["\rfoo", "\nfoo"],
+                     ["foo\r", "foo\n"],
+                     ["foo\rbar", "foo\nbar"],
+                     ["foo\rbar\r", "foo\nbar\n"],
+                     ["\r\n", "\n"],
+                     ["\r\nfoo", "\nfoo"],
+                     ["foo\r\n", "foo\n"],
+                     ["foo\r\nbar", "foo\nbar"],
+                     ["foo\r\nbar\r\n", "foo\nbar\n"] ];
+
+var value_append_tests = [ ["foo", "bar", "foobar"],
+                           ["foo", "foo", "foofoo"],
+                           ["foobar", "bar", "foobarbar"],
+                           ["foobar", "foo", "foobarfoo"],
+                           ["foo\n", "foo", "foo\nfoo"],
+                           ["foo\r", "foo", "foo\nfoo"],
+                           ["foo\r\n", "foo", "foo\nfoo"],
+                           ["\n", "\n", "\n\n"],
+                           ["\r", "\r", "\n\n"],
+                           ["\r\n", "\r\n", "\n\n"],
+                           ["\r", "\r\n", "\n\n"],
+                           ["\r\n", "\r", "\n\n"],
+                           [null, null, "null"],
+                           [null, undefined, "undefined"],
+                           ["", "", ""]
+                           ];
+
+
+var simple_tests_for_input = [ ["foo", "foo"],
+                               ["", ""],
+                               [null, ""],
+                               [undefined , "undefined"],
+                               ["\n", ""],
+                               ["\r", ""],
+                               ["\rfoo", " foo"],
+                               ["foo\r", "foo"],
+                               ["foo\rbar", "foo bar"],
+                               ["foo\rbar\r", "foo bar"],
+                               ["\r\n", ""],
+                               ["\r\nfoo", " foo"],
+                               ["foo\r\n", "foo"],
+                               ["foo\r\nbar", "foo bar"],
+                               ["foo\r\nbar\r\n", "foo bar"] ];
+
+var value_append_tests_for_input = [ ["foo", "bar", "foobar"],
+                                     ["foo", "foo", "foofoo"],
+                                     ["foobar", "bar", "foobarbar"],
+                                     ["foobar", "foo", "foobarfoo"],
+                                     ["foo\n", "foo", "foofoo"],
+                                     ["foo\r", "foo", "foofoo"],
+                                     ["foo\r\n", "foo", "foofoo"],
+                                     ["\n", "\n", ""],
+                                     ["\r", "\r", ""],
+                                     ["\r\n", "\r\n", ""],
+                                     ["\r", "\r\n", ""],
+                                     ["\r\n", "\r", ""],
+                                     [null, null, "null"],
+                                     [null, undefined, "undefined"],
+                                     ["", "", ""]
+                                     ];
+function runTestsFor(el, simpleTests, appendTests) {
+  for(var i = 0; i < simpleTests.length; ++i) {
+    el.value = simpleTests[i][0];
+    is(el.value, simpleTests[i][1], "Wrong value (wrap=" + el.getAttribute('wrap') + ", simple_test=" + i + ")");
+  }
+  for (var j = 0; j < appendTests.length; ++j) {
+    el.value = appendTests[j][0];
+    el.value += appendTests[j][1];
+    is(el.value, appendTests[j][2], "Wrong value (wrap=" + el.getAttribute('wrap') + ", value_append_test=" + j + ")");
+  }
+}
+
+function runTests() {
+  var textareas = document.getElementsByTagName("textarea");
+  for (var i = 0; i < textareas.length; ++i) {
+    runTestsFor(textareas[i], simple_tests, value_append_tests);
+  }
+  runTestsFor(document.getElementsByTagName("input")[0],
+              simple_tests_for_input, value_append_tests_for_input);
+  SimpleTest.finish();
+}
+
+
+</script>
+</pre>
+<textarea cols="30" rows="7" wrap="none"></textarea>
+<textarea cols="30" rows="7" wrap="off"></textarea><br>
+<textarea cols="30" rows="7" wrap="soft"></textarea>
+<textarea cols="30" rows="7" wrap="hard"></textarea>
+<input type="text">
+</body>
+</html>
--- a/content/html/document/src/nsHTMLDocument.cpp
+++ b/content/html/document/src/nsHTMLDocument.cpp
@@ -2275,27 +2275,28 @@ nsHTMLDocument::MatchNameAttribute(nsICo
     aContent->AttrValueIs(kNameSpaceID_None, nsGkAtoms::name,
                           *elementName, eCaseMatters);
 }
 
 NS_IMETHODIMP
 nsHTMLDocument::GetElementsByName(const nsAString& aElementName,
                                   nsIDOMNodeList** aReturn)
 {
-  void* elementNameData = new nsString(aElementName);
+  nsString* elementNameData = new nsString(aElementName);
   NS_ENSURE_TRUE(elementNameData, NS_ERROR_OUT_OF_MEMORY);
   nsContentList* elements =
-    new nsContentList(this,
-                      MatchNameAttribute,
-                      nsContentUtils::DestroyMatchString,
-                      elementNameData);
+    NS_GetFuncStringContentList(this,
+                                MatchNameAttribute,
+                                nsContentUtils::DestroyMatchString,
+                                elementNameData,
+                                *elementNameData).get();
   NS_ENSURE_TRUE(elements, NS_ERROR_OUT_OF_MEMORY);
 
+  // Transfer ownership
   *aReturn = elements;
-  NS_ADDREF(*aReturn);
 
   return NS_OK;
 }
 
 void
 nsHTMLDocument::ScriptLoading(nsIScriptElement *aScript)
 {
   if (mWriteState == eNotWriting) {
--- a/content/media/ogg/nsChannelReader.h
+++ b/content/media/ogg/nsChannelReader.h
@@ -49,17 +49,17 @@ class nsMediaDecoder;
 
 class nsChannelReader : public OggPlayReader
 {
 public:
   nsChannelReader();
   ~nsChannelReader();
 
   /**
-   * Initialize the reader with the edia stream.
+   * Initialize the reader with the media stream.
    * This takes ownership of aStream.
    */
   void Init(nsMediaStream* aStream);
 
   nsMediaStream* Stream() { return mStream; }
 
   // Set the time of the last frame. This is returned in duration() to
   // liboggplay. Call with decoder lock obtained so that liboggplay cannot
--- a/content/media/test/Makefile.in
+++ b/content/media/test/Makefile.in
@@ -93,16 +93,17 @@ include $(topsrcdir)/config/rules.mk
 		test_currentTime.html \
 		test_decode_error.html \
 		test_decoder_disable.html \
 		test_load.html \
 		test_media_selection.html \
 		test_mozLoadFrom.html \
 		test_networkState.html \
 		test_paused.html \
+		test_play_twice.html \
 		test_playback.html \
 		test_playback_errors.html \
 		test_reactivate.html \
 		test_readyState.html \
 		test_seek2.html \
 		test_volume.html \
 		use_large_cache.js \
 		$(NULL)
@@ -143,16 +144,17 @@ endif
 		bug504843.ogv \
 		bug506094.ogv \
 		bug516323.ogv \
 		bug520493.ogg \
 		bug520500.ogg \
 		bug520908.ogv \
 		bug520908.ogv^headers^ \
 		bug523816.ogv \
+		bug533822.ogg \
 		chain.ogv \
 		dirac.ogg \
 		seek.ogv \
 		short-video.ogv \
 		small-shot.ogg \
 		sound.ogg \
 		$(NULL)
 
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..a8e506910e6c031fe42aadd4cab0abf33959f6ad
GIT binary patch
literal 35010
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
HeFp&mF7I{A
--- a/content/media/test/manifest.js
+++ b/content/media/test/manifest.js
@@ -12,16 +12,22 @@ var gSmallTests = [
 
 // Used by test_mozLoadFrom.  Need one test file per decoder backend, plus
 // anything for testing clone-specific bugs.
 var gCloneTests = gSmallTests.concat([
   // Actual duration is ~200ms, we have Content-Duration lie about it.
   { name:"bug520908.ogv", type:"video/ogg", duration:9000 },
 ]);
 
+// Used by test_play_twice.  Need one test file per decoder backend, plus
+// anything for testing bugs that occur when replying a played file.
+var gReplayTests = gSmallTests.concat([
+  { name:"bug533822.ogg", type:"audio/ogg" },
+]);
+
 // These are files that we want to make sure we can play through.  We can
 // also check metadata.  Put files of the same type together in this list so if
 // something crashes we have some idea of which backend is responsible.
 // Used by test_playback, which expects no error event and one ended event.
 var gPlayTests = [
   // 8-bit samples
   { name:"r11025_u8_c1.wav", type:"audio/x-wav", duration:1.0 },
   // 8-bit samples, file is truncated
new file mode 100644
--- /dev/null
+++ b/content/media/test/test_play_twice.html
@@ -0,0 +1,93 @@
+<!DOCTYPE HTML>
+<html>
+<head>
+  <title>Test playback of media files that should play OK</title>
+  <script type="text/javascript" src="/MochiKit/packed.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+  <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
+  <script type="text/javascript" src="manifest.js"></script>
+</head>
+<body>
+<pre id="test">
+<script class="testbody" type="text/javascript">
+var PARALLEL_TESTS = 2;
+
+var testIndex = 0;
+var videos = [];
+
+var testsWaiting = 0;
+
+function startTests() {
+  for (var i = 0; i < videos.length; ++i) {
+    document.body.removeChild(videos[i]);
+  }
+  videos = [];
+  while (videos.length < PARALLEL_TESTS && testIndex < gReplayTests.length) {
+    var v = document.createElement('video');
+    var test = gReplayTests[testIndex];
+    ++testIndex;
+    if (!v.canPlayType(test.type))
+      continue;
+
+    v.src = test.name;
+    var check = function(test, v) { return function() {
+      checkMetadata(test.name, v, test);
+    }}(test, v);
+    var noLoad = function(test, v) { return function() {
+      ok(false, test.name + " should not fire 'load' event");
+    }}(test, v);
+    var checkEnded = function(test, v) { return function() {
+      if (test.duration) {
+        ok(Math.abs(v.currentTime - test.duration) < 0.1,
+           test.name + " current time at end: " + v.currentTime);
+      }
+      is(v.readyState, v.HAVE_CURRENT_DATA, test.name + " checking readyState");
+      ok(v.readyState != v.NETWORK_LOADED, test.name + " shouldn't report NETWORK_LOADED");
+      ok(v.ended, test.name + " checking playback has ended");
+      if (v._playedOnce) {
+        --testsWaiting;
+        if (testsWaiting == 0) {
+          setTimeout(startTests, 0);
+        }
+      } else {
+        v._playedOnce = true;
+        v.play();
+      }
+    }}(test, v);
+    var checkSuspended = function(test, v) { return function() {
+      if (v.seenSuspend)
+        return;
+
+      v.seenSuspend = true;
+      ok(true, test.name + " got suspend");
+      --testsWaiting;
+      if (testsWaiting == 0) {
+        setTimeout(startTests, 0);
+      }
+    }}(test, v);
+    v.addEventListener("load", noLoad, false);
+    v.addEventListener("loadedmetadata", check, false);
+
+    // We should get "ended" and "suspend" events for every resource
+    v.addEventListener("ended", checkEnded, false);
+    v.addEventListener("suspend", checkSuspended, false);
+    testsWaiting += 2;
+
+    document.body.appendChild(v);
+    v.play();
+    videos.push(v);
+  }
+  if (videos.length == 0) {
+    // No new tests were spawned, perhaps the remaining tests on the list are
+    // not supported, or we just reached the end of the list.
+    SimpleTest.finish();
+  }
+}
+
+SimpleTest.waitForExplicitFinish();
+
+addLoadEvent(startTests);
+</script>
+</pre>
+</body>
+</html>
--- a/content/smil/nsSMILAnimationFunction.cpp
+++ b/content/smil/nsSMILAnimationFunction.cpp
@@ -863,27 +863,27 @@ nsSMILAnimationFunction::CheckKeySplines
 
 PRBool
 nsSMILAnimationFunction::GetAccumulate() const
 {
   const nsAttrValue* value = GetAttr(nsGkAtoms::accumulate);
   if (!value)
     return PR_FALSE;
 
-  return (value->GetEnumValue() == PR_TRUE);
+  return value->GetEnumValue();
 }
 
 PRBool
 nsSMILAnimationFunction::GetAdditive() const
 {
   const nsAttrValue* value = GetAttr(nsGkAtoms::additive);
   if (!value)
     return PR_FALSE;
 
-  return (value->GetEnumValue() == PR_TRUE);
+  return value->GetEnumValue();
 }
 
 nsSMILAnimationFunction::nsSMILCalcMode
 nsSMILAnimationFunction::GetCalcMode() const
 {
   const nsAttrValue* value = GetAttr(nsGkAtoms::calcMode);
   if (!value)
     return CALC_LINEAR;
--- a/content/svg/content/src/nsSVGElement.cpp
+++ b/content/svg/content/src/nsSVGElement.cpp
@@ -1521,16 +1521,28 @@ nsSVGElement::DidChangePreserveAspectRat
 
   nsAutoString newStr;
   preserveAspectRatio->GetBaseValueString(newStr);
 
   SetAttr(kNameSpaceID_None, nsGkAtoms::preserveAspectRatio,
           newStr, PR_TRUE);
 }
 
+void
+nsSVGElement::DidAnimatePreserveAspectRatio()
+{
+  nsIFrame* frame = GetPrimaryFrame();
+  
+  if (frame) {
+    frame->AttributeChanged(kNameSpaceID_None,
+                            nsGkAtoms::preserveAspectRatio,
+                            nsIDOMMutationEvent::MODIFICATION);
+  }
+}
+
 nsSVGElement::StringAttributesInfo
 nsSVGElement::GetStringInfo()
 {
   return StringAttributesInfo(nsnull, nsnull, 0);
 }
 
 void nsSVGElement::StringAttributesInfo::Reset(PRUint8 aAttrEnum)
 {
@@ -1744,16 +1756,22 @@ nsSVGElement::GetAnimatedAttr(const nsIA
     BooleanAttributesInfo info = GetBooleanInfo();
     for (PRUint32 i = 0; i < info.mBooleanCount; i++) {
       if (aName == *info.mBooleanInfo[i].mName) {
         return info.mBooleans[i].ToSMILAttr(this);
       }
     }
   }
 
+  // preserveAspectRatio:
+  if (aName == nsGkAtoms::preserveAspectRatio) {
+    nsSVGPreserveAspectRatio *preserveAspectRatio = GetPreserveAspectRatio();
+    return preserveAspectRatio ? preserveAspectRatio->ToSMILAttr(this) : nsnull;
+  }
+
   return nsnull;
 }
 
 void
 nsSVGElement::AnimationNeedsResample()
 {
   nsIDocument* doc = GetCurrentDoc();
   if (doc) {
--- a/content/svg/content/src/nsSVGElement.h
+++ b/content/svg/content/src/nsSVGElement.h
@@ -154,16 +154,17 @@ public:
   virtual void DidChangeViewBox(PRBool aDoSetAttr);
   virtual void DidChangePreserveAspectRatio(PRBool aDoSetAttr);
   virtual void DidChangeString(PRUint8 aAttrEnum) {}
 
   virtual void DidAnimateLength(PRUint8 aAttrEnum);
   virtual void DidAnimateNumber(PRUint8 aAttrEnum);
   virtual void DidAnimateBoolean(PRUint8 aAttrEnum);
   virtual void DidAnimateEnum(PRUint8 aAttrEnum);
+  virtual void DidAnimatePreserveAspectRatio();
 
   void GetAnimatedLengthValues(float *aFirst, ...);
   void GetAnimatedNumberValues(float *aFirst, ...);
   void GetAnimatedIntegerValues(PRInt32 *aFirst, ...);
 
 #ifdef MOZ_SMIL
   virtual nsISMILAttr* GetAnimatedAttr(const nsIAtom* aName);
   void AnimationNeedsResample();
--- a/content/svg/content/src/nsSVGFilters.cpp
+++ b/content/svg/content/src/nsSVGFilters.cpp
@@ -325,16 +325,22 @@ nsSVGFE::DidAnimateNumber(PRUint8 aAttrE
 
 void
 nsSVGFE::DidAnimateEnum(PRUint8 aAttrEnum)
 {
   DidAnimateAttr(this);
 }
 
 void
+nsSVGFE::DidAnimatePreserveAspectRatio(PRUint8 aAttrEnum)
+{
+  DidAnimateAttr(this);
+}
+
+void
 nsSVGFE::DidAnimateBoolean(PRUint8 aAttrEnum)
 {
   DidAnimateAttr(this);
 }
 
 //---------------------Gaussian Blur------------------------
 
 typedef nsSVGFE nsSVGFEGaussianBlurElementBase;
@@ -4820,29 +4826,33 @@ nsSVGFELightingElement::Filter(nsSVGFilt
   }
   float lightPos[3], pointsAt[3], specularExponent, cosConeAngle;
   if (pointLight) {
     static_cast<nsSVGFEPointLightElement*>
       (pointLight.get())->GetAnimatedNumberValues(lightPos,
                                                   lightPos + 1,
                                                   lightPos + 2,
                                                   nsnull);
+    instance->ConvertLocation(lightPos);
   }
   if (spotLight) {
     float limitingConeAngle;
     static_cast<nsSVGFESpotLightElement*>
       (spotLight.get())->GetAnimatedNumberValues(lightPos,
                                                  lightPos + 1,
                                                  lightPos + 2,
                                                  pointsAt,
                                                  pointsAt + 1,
                                                  pointsAt + 2,
                                                  &specularExponent,
                                                  &limitingConeAngle,
                                                  nsnull);
+    instance->ConvertLocation(lightPos);
+    instance->ConvertLocation(pointsAt);
+
     nsCOMPtr<nsIContent> spot = do_QueryInterface(spotLight);
     if (spot->HasAttr(kNameSpaceID_None, nsGkAtoms::limitingConeAngle)) {
       cosConeAngle = NS_MAX<double>(cos(limitingConeAngle * radPerDeg), 0.0);
     } else {
       cosConeAngle = 0;
     }
   }
 
@@ -5454,17 +5464,18 @@ nsSVGFEImageElement::Filter(nsSVGFilterI
 
     PRInt32 nativeWidth, nativeHeight;
     imageContainer->GetWidth(&nativeWidth);
     imageContainer->GetHeight(&nativeHeight);
 
     const gfxRect& filterSubregion = aTarget->mFilterPrimitiveSubregion;
 
     gfxMatrix viewBoxTM =
-      nsSVGUtils::GetViewBoxTransform(filterSubregion.Width(), filterSubregion.Height(),
+      nsSVGUtils::GetViewBoxTransform(this,
+                                      filterSubregion.Width(), filterSubregion.Height(),
                                       0,0, nativeWidth, nativeHeight,
                                       mPreserveAspectRatio);
 
     gfxMatrix xyTM = gfxMatrix().Translate(gfxPoint(filterSubregion.X(), filterSubregion.Y()));
 
     gfxMatrix TM = viewBoxTM * xyTM;
     
     gfxContext ctx(aTarget->mImage);
--- a/content/svg/content/src/nsSVGFilters.h
+++ b/content/svg/content/src/nsSVGFilters.h
@@ -216,16 +216,17 @@ protected:
   }
 
   // nsSVGElement specializations:
   virtual LengthAttributesInfo GetLengthInfo();
   virtual void DidAnimateLength(PRUint8 aAttrEnum);
   virtual void DidAnimateNumber(PRUint8 aAttrEnum);
   virtual void DidAnimateEnum(PRUint8 aAttrEnum);
   virtual void DidAnimateBoolean(PRUint8 aAttrEnum);
+  virtual void DidAnimatePreserveAspectRatio(PRUint8 aAttrEnum);
 
   // nsIDOMSVGFitlerPrimitiveStandardAttributes values
   enum { X, Y, WIDTH, HEIGHT };
   nsSVGLength2 mLengthAttributes[4];
   static LengthInfo sLengthInfo[4];
 };
 
 #endif
--- a/content/svg/content/src/nsSVGMarkerElement.cpp
+++ b/content/svg/content/src/nsSVGMarkerElement.cpp
@@ -409,17 +409,18 @@ nsSVGMarkerElement::GetViewBoxTransform(
     if (viewbox.width <= 0.0f || viewbox.height <= 0.0f) {
       return gfxMatrix(0.0, 0.0, 0.0, 0.0, 0.0, 0.0); // invalid - don't paint element
     }
 
     float refX = mLengthAttributes[REFX].GetAnimValue(mCoordCtx);
     float refY = mLengthAttributes[REFY].GetAnimValue(mCoordCtx);
 
     gfxMatrix viewBoxTM =
-      nsSVGUtils::GetViewBoxTransform(viewportWidth, viewportHeight,
+      nsSVGUtils::GetViewBoxTransform(this,
+                                      viewportWidth, viewportHeight,
                                       viewbox.x, viewbox.y,
                                       viewbox.width, viewbox.height,
                                       mPreserveAspectRatio,
                                       PR_TRUE);
 
     gfxPoint ref = viewBoxTM.Transform(gfxPoint(refX, refY));
 
     gfxMatrix TM = viewBoxTM * gfxMatrix().Translate(gfxPoint(-ref.x, -ref.y));
--- a/content/svg/content/src/nsSVGPreserveAspectRatio.cpp
+++ b/content/svg/content/src/nsSVGPreserveAspectRatio.cpp
@@ -33,16 +33,22 @@
  * and other provisions required by the GPL or the LGPL. If you do not delete
  * the provisions above, a recipient may use your version of this file under
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 
 #include "nsSVGPreserveAspectRatio.h"
 #include "nsWhitespaceTokenizer.h"
+#ifdef MOZ_SMIL
+#include "nsSMILValue.h"
+#include "SMILEnumType.h"
+#endif // MOZ_SMIL
+
+using namespace mozilla;
 
 ////////////////////////////////////////////////////////////////////////
 // nsSVGPreserveAspectRatio class
 
 NS_SVG_VAL_IMPL_CYCLE_COLLECTION(
   nsSVGPreserveAspectRatio::DOMBaseVal, mSVGElement)
 NS_SVG_VAL_IMPL_CYCLE_COLLECTION(
   nsSVGPreserveAspectRatio::DOMAnimVal, mSVGElement)
@@ -153,38 +159,36 @@ nsSVGPreserveAspectRatio::ToDOMAnimVal(n
   *aResult = new DOMAnimVal(this, aSVGElement);
   if (!*aResult)
     return NS_ERROR_OUT_OF_MEMORY;
 
   NS_ADDREF(*aResult);
   return NS_OK;
 }
 
-nsresult
-nsSVGPreserveAspectRatio::SetBaseValueString(const nsAString &aValueAsString,
-                                             nsSVGElement *aSVGElement,
-                                             PRBool aDoSetAttr)
+static nsresult
+ToPreserveAspectRatio(const nsAString &aString,
+                      nsSVGPreserveAspectRatio::PreserveAspectRatio *aValue)
 {
-  if (aValueAsString.IsEmpty() ||
-      NS_IsAsciiWhitespace(aValueAsString[0])) {
+  if (aString.IsEmpty() || NS_IsAsciiWhitespace(aString[0])) {
     return NS_ERROR_DOM_SYNTAX_ERR;
   }
 
-  nsWhitespaceTokenizer tokenizer(aValueAsString);
+  nsWhitespaceTokenizer tokenizer(aString);
   if (!tokenizer.hasMoreTokens()) {
     return NS_ERROR_DOM_SYNTAX_ERR;
   }
   const nsAString &token = tokenizer.nextToken();
 
   nsresult rv;
-  PreserveAspectRatio val;
+  nsSVGPreserveAspectRatio::PreserveAspectRatio val;
 
-  val.mDefer = token.EqualsLiteral("defer");
+  val.SetDefer(token.EqualsLiteral("defer"));
 
-  if (val.mDefer) {
+  if (val.GetDefer()) {
     if (!tokenizer.hasMoreTokens()) {
       return NS_ERROR_DOM_SYNTAX_ERR;
     }
     rv = val.SetAlign(GetAlignForString(tokenizer.nextToken()));
   } else {
     rv = val.SetAlign(GetAlignForString(token));
   }
 
@@ -193,25 +197,45 @@ nsSVGPreserveAspectRatio::SetBaseValueSt
   }
 
   if (tokenizer.hasMoreTokens()) {
     rv = val.SetMeetOrSlice(GetMeetOrSliceForString(tokenizer.nextToken()));
     if (NS_FAILED(rv)) {
       return NS_ERROR_DOM_SYNTAX_ERR;
     }
   } else {
-    val.mMeetOrSlice = nsIDOMSVGPreserveAspectRatio::SVG_MEETORSLICE_MEET;
+    val.SetMeetOrSlice(nsIDOMSVGPreserveAspectRatio::SVG_MEETORSLICE_MEET);
   }
 
   if (tokenizer.hasMoreTokens()) {
     return NS_ERROR_DOM_SYNTAX_ERR;
   }
 
+  *aValue = val;
+  return NS_OK;
+}
+
+nsresult
+nsSVGPreserveAspectRatio::SetBaseValueString(const nsAString &aValueAsString,
+                                             nsSVGElement *aSVGElement,
+                                             PRBool aDoSetAttr)
+{
+  PreserveAspectRatio val;
+  nsresult res = ToPreserveAspectRatio(aValueAsString, &val);
+  if (NS_FAILED(res)) {
+    return res;
+  }
+
   mAnimVal = mBaseVal = val;
   aSVGElement->DidChangePreserveAspectRatio(aDoSetAttr);
+#ifdef MOZ_SMIL
+  if (mIsAnimated) {
+    aSVGElement->AnimationNeedsResample();
+  }
+#endif
   return NS_OK;
 }
 
 void
 nsSVGPreserveAspectRatio::GetBaseValueString(nsAString & aValueAsString)
 {
   nsAutoString tmpString;
 
@@ -237,37 +261,121 @@ nsresult
 nsSVGPreserveAspectRatio::SetBaseAlign(PRUint16 aAlign,
                                        nsSVGElement *aSVGElement)
 {
   nsresult rv = mBaseVal.SetAlign(aAlign);
   NS_ENSURE_SUCCESS(rv, rv);
 
   mAnimVal.mAlign = mBaseVal.mAlign;
   aSVGElement->DidChangePreserveAspectRatio(PR_TRUE);
-
+#ifdef MOZ_SMIL
+  if (mIsAnimated) {
+    aSVGElement->AnimationNeedsResample();
+  }
+#endif
+  
   return NS_OK;
 }
 
 nsresult
 nsSVGPreserveAspectRatio::SetBaseMeetOrSlice(PRUint16 aMeetOrSlice,
                                              nsSVGElement *aSVGElement)
 {
   nsresult rv = mBaseVal.SetMeetOrSlice(aMeetOrSlice);
   NS_ENSURE_SUCCESS(rv, rv);
 
   mAnimVal.mMeetOrSlice = mBaseVal.mMeetOrSlice;
   aSVGElement->DidChangePreserveAspectRatio(PR_TRUE);
+#ifdef MOZ_SMIL
+  if (mIsAnimated) {
+    aSVGElement->AnimationNeedsResample();
+  }
+#endif
+  
+  return NS_OK;
+}
 
-  return NS_OK;
+void
+nsSVGPreserveAspectRatio::SetAnimValue(PRUint64 aPackedValue, nsSVGElement *aSVGElement)
+{
+  mAnimVal.SetDefer(((aPackedValue & 0xff0000) >> 16) ? PR_TRUE : PR_FALSE);
+  mAnimVal.SetAlign(PRUint16((aPackedValue & 0xff00) >> 8));
+  mAnimVal.SetMeetOrSlice(PRUint16(aPackedValue & 0xff));
+  mIsAnimated = PR_TRUE;
+  aSVGElement->DidAnimatePreserveAspectRatio();
 }
 
 nsresult
 nsSVGPreserveAspectRatio::ToDOMAnimatedPreserveAspectRatio(
   nsIDOMSVGAnimatedPreserveAspectRatio **aResult,
   nsSVGElement *aSVGElement)
 {
   *aResult = new DOMAnimPAspectRatio(this, aSVGElement);
   if (!*aResult)
     return NS_ERROR_OUT_OF_MEMORY;
 
   NS_ADDREF(*aResult);
   return NS_OK;
 }
+
+#ifdef MOZ_SMIL
+nsISMILAttr*
+nsSVGPreserveAspectRatio::ToSMILAttr(nsSVGElement *aSVGElement)
+{
+  return new SMILPreserveAspectRatio(this, aSVGElement);
+}
+
+static PRUint64
+PackPreserveAspectRatio(const nsSVGPreserveAspectRatio::PreserveAspectRatio& par)
+{
+  // All preserveAspectRatio values are enum values (do not interpolate), so we
+  // can safely collate them and treat them as a single enum as for SMIL.
+  PRUint64 packed = 0;
+  packed |= PRUint64(par.GetDefer() ? 1 : 0) << 16;
+  packed |= PRUint64(par.GetAlign()) << 8;
+  packed |= PRUint64(par.GetMeetOrSlice());
+  return packed;
+}
+
+nsresult
+nsSVGPreserveAspectRatio::SMILPreserveAspectRatio
+                        ::ValueFromString(const nsAString& aStr,
+                                          const nsISMILAnimationElement* /*aSrcElement*/,
+                                          nsSMILValue& aValue) const
+{
+  PreserveAspectRatio par;
+  nsresult res = ToPreserveAspectRatio(aStr, &par);
+  NS_ENSURE_SUCCESS(res, res);
+
+  nsSMILValue val(&SMILEnumType::sSingleton);
+  val.mU.mUint = PackPreserveAspectRatio(par);
+  aValue = val;
+  return NS_OK;
+}
+
+nsSMILValue
+nsSVGPreserveAspectRatio::SMILPreserveAspectRatio::GetBaseValue() const
+{
+  nsSMILValue val(&SMILEnumType::sSingleton);
+  val.mU.mUint = PackPreserveAspectRatio(mVal->GetBaseValue());
+  return val;
+}
+
+void
+nsSVGPreserveAspectRatio::SMILPreserveAspectRatio::ClearAnimValue()
+{
+  if (mVal->mIsAnimated) {
+    mVal->SetAnimValue(PackPreserveAspectRatio(mVal->GetBaseValue()), mSVGElement);
+    mVal->mIsAnimated = PR_FALSE;
+  }
+}
+
+nsresult
+nsSVGPreserveAspectRatio::SMILPreserveAspectRatio::SetAnimValue(const nsSMILValue& aValue)
+{
+  NS_ASSERTION(aValue.mType == &SMILEnumType::sSingleton,
+               "Unexpected type to assign animated value");
+  if (aValue.mType == &SMILEnumType::sSingleton) {
+    mVal->SetAnimValue(aValue.mU.mUint, mSVGElement);
+  }
+  return NS_OK;
+}
+#endif // MOZ_SMIL
--- a/content/svg/content/src/nsSVGPreserveAspectRatio.h
+++ b/content/svg/content/src/nsSVGPreserveAspectRatio.h
@@ -90,38 +90,51 @@ public:
     PRPackedBool mDefer;
   };
 
   void Init() {
     mBaseVal.mAlign = nsIDOMSVGPreserveAspectRatio::SVG_PRESERVEASPECTRATIO_XMIDYMID;
     mBaseVal.mMeetOrSlice = nsIDOMSVGPreserveAspectRatio::SVG_MEETORSLICE_MEET;
     mBaseVal.mDefer = PR_FALSE;
     mAnimVal = mBaseVal;
+    mIsAnimated = PR_FALSE;
   }
 
   nsresult SetBaseValueString(const nsAString& aValue,
                               nsSVGElement *aSVGElement,
                               PRBool aDoSetAttr);
   void GetBaseValueString(nsAString& aValue);
 
   nsresult SetBaseAlign(PRUint16 aAlign, nsSVGElement *aSVGElement);
   nsresult SetBaseMeetOrSlice(PRUint16 aMeetOrSlice, nsSVGElement *aSVGElement);
+  void SetAnimValue(PRUint64 aPackedValue, nsSVGElement *aSVGElement);
+
   const PreserveAspectRatio &GetBaseValue() const
     { return mBaseVal; }
-  const PreserveAspectRatio &GetAnimValue() const
-    { return mAnimVal; }
+  const PreserveAspectRatio &GetAnimValue(nsSVGElement *aSVGElement) const
+  {
+#ifdef MOZ_SMIL
+    aSVGElement->FlushAnimations();
+#endif
+    return mAnimVal;
+  }
 
   nsresult ToDOMAnimatedPreserveAspectRatio(
     nsIDOMSVGAnimatedPreserveAspectRatio **aResult,
     nsSVGElement* aSVGElement);
+#ifdef MOZ_SMIL
+  // Returns a new nsISMILAttr object that the caller must delete
+  nsISMILAttr* ToSMILAttr(nsSVGElement* aSVGElement);
+#endif // MOZ_SMIL
 
 private:
 
   PreserveAspectRatio mAnimVal;
   PreserveAspectRatio mBaseVal;
+  PRPackedBool mIsAnimated;
 
   nsresult ToDOMBaseVal(nsIDOMSVGPreserveAspectRatio **aResult,
                         nsSVGElement* aSVGElement);
   nsresult ToDOMAnimVal(nsIDOMSVGPreserveAspectRatio **aResult,
                         nsSVGElement* aSVGElement);
 
   struct DOMBaseVal : public nsIDOMSVGPreserveAspectRatio
   {
@@ -152,22 +165,22 @@ private:
 
     DOMAnimVal(nsSVGPreserveAspectRatio* aVal, nsSVGElement *aSVGElement)
       : mVal(aVal), mSVGElement(aSVGElement) {}
     
     nsSVGPreserveAspectRatio* mVal; // kept alive because it belongs to mSVGElement
     nsRefPtr<nsSVGElement> mSVGElement;
     
     NS_IMETHOD GetAlign(PRUint16* aAlign)
-      { *aAlign = mVal->GetAnimValue().GetAlign(); return NS_OK; }
+      { *aAlign = mVal->GetAnimValue(mSVGElement).GetAlign(); return NS_OK; }
     NS_IMETHOD SetAlign(PRUint16 aAlign)
       { return NS_ERROR_DOM_NO_MODIFICATION_ALLOWED_ERR; }
 
     NS_IMETHOD GetMeetOrSlice(PRUint16* aMeetOrSlice)
-      { *aMeetOrSlice = mVal->GetAnimValue().GetMeetOrSlice(); return NS_OK; }
+      { *aMeetOrSlice = mVal->GetAnimValue(mSVGElement).GetMeetOrSlice(); return NS_OK; }
     NS_IMETHOD SetMeetOrSlice(PRUint16 aValue)
       { return NS_ERROR_DOM_NO_MODIFICATION_ALLOWED_ERR; }
   };
 
   struct DOMAnimPAspectRatio : public nsIDOMSVGAnimatedPreserveAspectRatio
   {
     NS_DECL_CYCLE_COLLECTING_ISUPPORTS
     NS_DECL_CYCLE_COLLECTION_CLASS(DOMAnimPAspectRatio)
@@ -180,11 +193,33 @@ private:
 
     NS_IMETHOD GetBaseVal(nsIDOMSVGPreserveAspectRatio **aBaseVal)
       { return mVal->ToDOMBaseVal(aBaseVal, mSVGElement); }
 
     NS_IMETHOD GetAnimVal(nsIDOMSVGPreserveAspectRatio **aAnimVal)
       { return mVal->ToDOMAnimVal(aAnimVal, mSVGElement); }
   };
 
+#ifdef MOZ_SMIL
+  struct SMILPreserveAspectRatio : public nsISMILAttr
+  {
+  public:
+    SMILPreserveAspectRatio(nsSVGPreserveAspectRatio* aVal, nsSVGElement* aSVGElement)
+      : mVal(aVal), mSVGElement(aSVGElement) {}
+
+    // These will stay alive because a nsISMILAttr only lives as long
+    // as the Compositing step, and DOM elements don't get a chance to
+    // die during that.
+    nsSVGPreserveAspectRatio* mVal;
+    nsSVGElement* mSVGElement;
+
+    // nsISMILAttr methods
+    virtual nsresult ValueFromString(const nsAString& aStr,
+                                     const nsISMILAnimationElement* aSrcElement,
+                                     nsSMILValue& aValue) const;
+    virtual nsSMILValue GetBaseValue() const;
+    virtual void ClearAnimValue();
+    virtual nsresult SetAnimValue(const nsSMILValue& aValue);
+  };
+#endif // MOZ_SMIL
 };
 
 #endif //__NS_SVGPRESERVEASPECTRATIO_H__
--- a/content/svg/content/src/nsSVGSVGElement.cpp
+++ b/content/svg/content/src/nsSVGSVGElement.cpp
@@ -995,17 +995,18 @@ nsSVGSVGElement::GetViewBoxTransform()
     viewBox.width  = viewportWidth;
     viewBox.height = viewportHeight;
   }
 
   if (viewBox.width <= 0.0f || viewBox.height <= 0.0f) {
     return gfxMatrix(0.0, 0.0, 0.0, 0.0, 0.0, 0.0); // singular
   }
 
-  return nsSVGUtils::GetViewBoxTransform(viewportWidth, viewportHeight,
+  return nsSVGUtils::GetViewBoxTransform(this,
+                                         viewportWidth, viewportHeight,
                                          viewBox.x, viewBox.y,
                                          viewBox.width, viewBox.height,
                                          mPreserveAspectRatio);
 }
 
 #ifdef MOZ_SMIL
 nsresult
 nsSVGSVGElement::BindToTree(nsIDocument* aDocument,
@@ -1220,13 +1221,21 @@ nsSVGSVGElement::GetViewBox()
 void
 nsSVGSVGElement::DidChangePreserveAspectRatio(PRBool aDoSetAttr)
 {
   nsSVGSVGElementBase::DidChangePreserveAspectRatio(aDoSetAttr);
 
   InvalidateTransformNotifyFrame();
 }
 
+void
+nsSVGSVGElement::DidAnimatePreserveAspectRatio()
+{
+  nsSVGSVGElementBase::DidAnimatePreserveAspectRatio();
+
+  InvalidateTransformNotifyFrame();
+}
+
 nsSVGPreserveAspectRatio *
 nsSVGSVGElement::GetPreserveAspectRatio()
 {
   return &mPreserveAspectRatio;
 }
--- a/content/svg/content/src/nsSVGSVGElement.h
+++ b/content/svg/content/src/nsSVGSVGElement.h
@@ -192,16 +192,18 @@ public:
 
   // nsSVGElement specializations:
   virtual gfxMatrix PrependLocalTransformTo(const gfxMatrix &aMatrix);
   virtual void DidChangeLength(PRUint8 aAttrEnum, PRBool aDoSetAttr);
   virtual void DidChangeEnum(PRUint8 aAttrEnum, PRBool aDoSetAttr);
   virtual void DidChangeViewBox(PRBool aDoSetAttr);
   virtual void DidChangePreserveAspectRatio(PRBool aDoSetAttr);
 
+  virtual void DidAnimatePreserveAspectRatio();
+  
   // nsSVGSVGElement methods:
   float GetLength(PRUint8 mCtxType);
   float GetMMPerPx(PRUint8 mCtxType = 0);
 
   // public helpers:
   gfxMatrix GetViewBoxTransform();
 
   virtual nsresult Clone(nsINodeInfo *aNodeInfo, nsINode **aResult) const;
--- a/content/xul/templates/src/nsXULTemplateQueryProcessorStorage.cpp
+++ b/content/xul/templates/src/nsXULTemplateQueryProcessorStorage.cpp
@@ -91,17 +91,17 @@ nsXULTemplateResultSetStorage::HasMoreEl
         return NS_OK;
     }
 
     nsresult rv = mStatement->ExecuteStep(aResult);
     NS_ENSURE_SUCCESS(rv, rv);
     // Because the nsXULTemplateResultSetStorage is owned by many nsXULTemplateResultStorage objects,
     // it could live longer than it needed to get results.
     // So we destroy the statement to free resources when all results are fetched
-    if (*aResult == PR_FALSE) {
+    if (!*aResult) {
         mStatement = nsnull;
     }
     return NS_OK;
 }
 
 NS_IMETHODIMP
 nsXULTemplateResultSetStorage::GetNext(nsISupports **aResult)
 {
--- a/docshell/base/nsDocShell.cpp
+++ b/docshell/base/nsDocShell.cpp
@@ -2107,18 +2107,18 @@ nsDocShell::GetLoadedTransIndex(PRInt32 
 NS_IMETHODIMP
 nsDocShell::HistoryPurged(PRInt32 aNumEntries)
 {
     // These indices are used for fastback cache eviction, to determine
     // which session history entries are candidates for content viewer
     // eviction.  We need to adjust by the number of entries that we
     // just purged from history, so that we look at the right session history
     // entries during eviction.
-    mPreviousTransIndex = PR_MAX(-1, mPreviousTransIndex - aNumEntries);
-    mLoadedTransIndex = PR_MAX(0, mLoadedTransIndex - aNumEntries);
+    mPreviousTransIndex = NS_MAX(-1, mPreviousTransIndex - aNumEntries);
+    mLoadedTransIndex = NS_MAX(0, mLoadedTransIndex - aNumEntries);
 
     PRInt32 count = mChildList.Count();
     for (PRInt32 i = 0; i < count; ++i) {
         nsCOMPtr<nsIDocShell> shell = do_QueryInterface(ChildAt(i));
         if (shell) {
             shell->HistoryPurged(aNumEntries);
         }
     }
@@ -6242,17 +6242,17 @@ nsDocShell::CanSavePresentation(PRUint32
         aLoadType != LOAD_STOP_CONTENT_AND_REPLACE &&
         aLoadType != LOAD_ERROR_PAGE)
         return PR_FALSE;
 
     // If the session history entry has the saveLayoutState flag set to false,
     // then we should not cache the presentation.
     PRBool canSaveState;
     mOSHE->GetSaveLayoutStateFlag(&canSaveState);
-    if (canSaveState == PR_FALSE)
+    if (!canSaveState)
         return PR_FALSE;
 
     // If the document is not done loading, don't cache it.
     nsCOMPtr<nsPIDOMWindow> pWin = do_QueryInterface(mScriptGlobal);
     if (!pWin || pWin->IsLoading())
         return PR_FALSE;
 
     if (pWin->WouldReuseInnerWindow(aNewDocument))
@@ -9511,17 +9511,17 @@ nsDocShell::AddToSessionHistory(nsIURI *
             PRUint32 expTime;         
             cacheEntryInfo->GetExpirationTime(&expTime);         
             PRUint32 now = PRTimeToSeconds(PR_Now());                  
             if (expTime <=  now)            
                 expired = PR_TRUE;         
          
         }
     }
-    if (expired == PR_TRUE)
+    if (expired)
         entry->SetExpirationStatus(PR_TRUE);
 
 
     if (root == static_cast<nsIDocShellTreeItem *>(this) && mSessionHistory) {
         // This is the root docshell
         if (LOAD_TYPE_HAS_FLAGS(mLoadType, LOAD_FLAGS_REPLACE_HISTORY)) {            
             // Replace current entry in session history.
             PRInt32  index = 0;   
--- a/docshell/build/Makefile.in
+++ b/docshell/build/Makefile.in
@@ -110,11 +110,11 @@ endif
 ifeq ($(MOZ_WIDGET_TOOLKIT),gtk2)
 EXTRA_DSO_LDOPTS	+= $(TK_LIBS)
 endif
 
 ifdef MOZ_ENABLE_DBUS
  EXTRA_DSO_LDOPTS += $(MOZ_DBUS_GLIB_LIBS)
 endif
 
-ifdef MOZ_PLATFORM_HILDON
-EXTRA_DSO_LDOPTS += $(LIBHILDONMIME_LIBS)
+ifdef MOZ_PLATFORM_MAEMO
+EXTRA_DSO_LDOPTS += $(MOZ_PLATFORM_MAEMO_LIBS)
 endif
--- a/docshell/shistory/src/nsSHistory.cpp
+++ b/docshell/shistory/src/nsSHistory.cpp
@@ -546,17 +546,17 @@ nsSHistory::SetMaxLength(PRInt32 aMaxSiz
 }
 
 NS_IMETHODIMP
 nsSHistory::PurgeHistory(PRInt32 aEntries)
 {
   if (mLength <= 0 || aEntries <= 0)
     return NS_ERROR_FAILURE;
 
-  aEntries = PR_MIN(aEntries, mLength);
+  aEntries = NS_MIN(aEntries, mLength);
   
   PRBool purgeHistory = PR_TRUE;
   // Notify the listener about the history purge
   if (mListener) {
     nsCOMPtr<nsISHistoryListener> listener(do_QueryReferent(mListener));
     if (listener) {
       listener->OnHistoryPurge(aEntries, &purgeHistory);
     } 
@@ -808,23 +808,23 @@ nsSHistory::EvictWindowContentViewers(PR
   // These indices give the range of SHEntries whose content viewers will be
   // evicted
   PRInt32 startIndex, endIndex;
   if (aToIndex > aFromIndex) { // going forward
     endIndex = aToIndex - gHistoryMaxViewers;
     if (endIndex <= 0) {
       return;
     }
-    startIndex = PR_MAX(0, aFromIndex - gHistoryMaxViewers);
+    startIndex = NS_MAX(0, aFromIndex - gHistoryMaxViewers);
   } else { // going backward
     startIndex = aToIndex + gHistoryMaxViewers + 1;
     if (startIndex >= mLength) {
       return;
     }
-    endIndex = PR_MIN(mLength, aFromIndex + gHistoryMaxViewers + 1);
+    endIndex = NS_MIN(mLength, aFromIndex + gHistoryMaxViewers + 1);
   }
 
 #ifdef DEBUG
   nsCOMPtr<nsISHTransaction> trans;
   GetTransactionAtIndex(0, getter_AddRefs(trans));
 
   // Walk the full session history and check that entries outside the window
   // around aFromIndex have no content viewers
@@ -908,18 +908,18 @@ nsSHistory::EvictGlobalContentViewer()
     PRInt32 totalContentViewers = 0;
     nsSHistory* shist = static_cast<nsSHistory*>
                                    (PR_LIST_HEAD(&gSHistoryList));
     while (shist != &gSHistoryList) {
       // Calculate the window of SHEntries that could possibly have a content
       // viewer.  There could be up to gHistoryMaxViewers content viewers,
       // but we don't know whether they are before or after the mIndex position
       // in the SHEntry list.  Just check both sides, to be safe.
-      PRInt32 startIndex = PR_MAX(0, shist->mIndex - gHistoryMaxViewers);
-      PRInt32 endIndex = PR_MIN(shist->mLength - 1,
+      PRInt32 startIndex = NS_MAX(0, shist->mIndex - gHistoryMaxViewers);
+      PRInt32 endIndex = NS_MIN(shist->mLength - 1,
                                 shist->mIndex + gHistoryMaxViewers);
       nsCOMPtr<nsISHTransaction> trans;
       shist->GetTransactionAtIndex(startIndex, getter_AddRefs(trans));
       
       for (PRInt32 i = startIndex; i <= endIndex; ++i) {
         nsCOMPtr<nsISHEntry> entry;
         trans->GetSHEntry(getter_AddRefs(entry));
         nsCOMPtr<nsIContentViewer> viewer;
@@ -1001,18 +1001,18 @@ nsSHistory::EvictGlobalContentViewer()
       shouldTryEviction = PR_FALSE;
     }
   }  // while shouldTryEviction
 }
 
 NS_IMETHODIMP
 nsSHistory::EvictExpiredContentViewerForEntry(nsISHEntry *aEntry)
 {
-  PRInt32 startIndex = PR_MAX(0, mIndex - gHistoryMaxViewers);
-  PRInt32 endIndex = PR_MIN(mLength - 1,
+  PRInt32 startIndex = NS_MAX(0, mIndex - gHistoryMaxViewers);
+  PRInt32 endIndex = NS_MIN(mLength - 1,
                             mIndex + gHistoryMaxViewers);
   nsCOMPtr<nsISHTransaction> trans;
   GetTransactionAtIndex(startIndex, getter_AddRefs(trans));
 
   PRInt32 i;
   for (i = startIndex; i <= endIndex; ++i) {
     nsCOMPtr<nsISHEntry> entry;
     trans->GetSHEntry(getter_AddRefs(entry));
--- a/dom/base/nsDOMClassInfo.cpp
+++ b/dom/base/nsDOMClassInfo.cpp
@@ -3594,16 +3594,17 @@ nsDOMClassInfo::Init()
     DOM_CLASSINFO_MAP_ENTRY(nsIDOMViewCSS)
     DOM_CLASSINFO_MAP_ENTRY(nsIDOMAbstractView)
     DOM_CLASSINFO_MAP_ENTRY(nsIDOMStorageWindow)
     DOM_CLASSINFO_MAP_ENTRY(nsIDOMModalContentWindow)
   DOM_CLASSINFO_MAP_END
 
   DOM_CLASSINFO_MAP_BEGIN(DataContainerEvent, nsIDOMDataContainerEvent)
     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDataContainerEvent)
+    DOM_CLASSINFO_EVENT_MAP_ENTRIES
   DOM_CLASSINFO_MAP_END
 
   DOM_CLASSINFO_MAP_BEGIN(MessageEvent, nsIDOMMessageEvent)
     DOM_CLASSINFO_MAP_ENTRY(nsIDOMMessageEvent)
     DOM_CLASSINFO_EVENT_MAP_ENTRIES
   DOM_CLASSINFO_MAP_END
 
   DOM_CLASSINFO_MAP_BEGIN(GeoGeolocation, nsIDOMGeoGeolocation)
--- a/dom/base/nsFocusManager.cpp
+++ b/dom/base/nsFocusManager.cpp
@@ -153,18 +153,17 @@ static NS_DEFINE_CID(kLookAndFeelCID, NS
 
 nsFocusManager* nsFocusManager::sInstance = nsnull;
 
 nsFocusManager::nsFocusManager()
 { }
 
 nsFocusManager::~nsFocusManager()
 {
-  nsCOMPtr<nsIPrefBranch2> prefBranch =
-    do_QueryInterface(nsContentUtils::GetPrefBranch());
+  nsIPrefBranch2* prefBranch = nsContentUtils::GetPrefBranch();
 
   if (prefBranch) {
     prefBranch->RemoveObserver("accessibility.browsewithcaret", this);
     prefBranch->RemoveObserver("accessibility.tabfocus_applies_to_xul", this);
   }
 }
 
 // static
@@ -175,18 +174,17 @@ nsFocusManager::Init()
   NS_ENSURE_TRUE(fm, NS_ERROR_OUT_OF_MEMORY);
   NS_ADDREF(fm);
   sInstance = fm;
 
   nsIContent::sTabFocusModelAppliesToXUL =
     nsContentUtils::GetBoolPref("accessibility.tabfocus_applies_to_xul",
                                 nsIContent::sTabFocusModelAppliesToXUL);
 
-  nsCOMPtr<nsIPrefBranch2> prefBranch =
-    do_QueryInterface(nsContentUtils::GetPrefBranch());
+  nsIPrefBranch2* prefBranch = nsContentUtils::GetPrefBranch();
   prefBranch->AddObserver("accessibility.browsewithcaret", fm, PR_TRUE);
   prefBranch->AddObserver("accessibility.tabfocus_applies_to_xul", fm, PR_TRUE);
 
   return NS_OK;
 }
 
 // static
 void
--- a/dom/interfaces/base/nsIContentPrefService.idl
+++ b/dom/interfaces/base/nsIContentPrefService.idl
@@ -60,39 +60,49 @@ interface nsIContentPrefObserver : nsISu
    * 
    * @param    aGroup      the group to which the pref belongs, or null
    *                       if it's a global pref (applies to all sites)
    * @param    aName       the name of the pref that was removed
    */
   void onContentPrefRemoved(in AString aGroup, in AString aName);
 };
 
-[scriptable, uuid(b3976fa1-189f-4fcb-9c3b-49d1f6d8073d)]
+[scriptable, function, uuid(c1b3d6df-5373-4606-8494-8bcf14a7fc62)]
+interface nsIContentPrefCallback : nsISupports
+{
+  void onResult(in nsIVariant aResult);
+};
+
+[scriptable, uuid(36715960-de39-457b-9d02-b800d5d3079b)]
 interface nsIContentPrefService : nsISupports
 {
   /**
    * Get a pref.
    *
    * Besides the regular string, integer, boolean, etc. values, this method
    * may return null (nsIDataType::VTYPE_EMPTY), which means the pref is set
    * to NULL in the database, as well as undefined (nsIDataType::VTYPE_VOID),
    * which means there is no record for this pref in the database.
    *
    * @param    aGroup      the group for which to get the pref, as an nsIURI
    *                       from which the hostname will be used, a string
    *                       (typically in the format of a hostname), or null 
    *                       to get the global pref (applies to all sites)
    * @param    aName       the name of the pref to get
+   * @param    aCallback   an optional nsIContentPrefCallback to receive the
+   *                       result. If desired, JavaScript callers can instead
+   *                       provide a function to call upon completion
    *
    * @returns  the value of the pref
    * @throws   NS_ERROR_ILLEGAL_VALUE if aGroup is not a string, nsIURI, or null
    * @throws   NS_ERROR_ILLEGAL_VALUE if aName is null or an empty string
    */
-  nsIVariant getPref(in nsIVariant aGroup, in AString aName);
-  
+  nsIVariant getPref(in nsIVariant aGroup, in AString aName,
+                     [optional] in nsIContentPrefCallback aCallback);
+
   /**
    * Set a pref.
    *
    * @param    aGroup      the group for which to set the pref, as an nsIURI
    *                       from which the hostname will be used, a string
    *                       (typically in the format of a hostname), or null
    *                       to set the global pref (applies to all sites)
    * @param    aName       the name of the pref to set
--- a/dom/plugins/PluginInstanceChild.cpp
+++ b/dom/plugins/PluginInstanceChild.cpp
@@ -49,16 +49,18 @@ using namespace mozilla::plugins;
 
 #ifdef MOZ_WIDGET_GTK2
 
 #include <gtk/gtk.h>
 #include <gdk/gdkx.h>
 #include <gdk/gdk.h>
 #include "gtk2xtbin.h"
 
+#elif defined(MOZ_WIDGET_QT)
+#include <QX11Info>
 #elif defined(OS_WIN)
 using mozilla::gfx::SharedDIB;
 
 #include <windows.h>
 
 #define NS_OOPP_DOUBLEPASS_MSGID TEXT("MozDoublePassMsg")
 #endif
 
@@ -72,16 +74,18 @@ PluginInstanceChild::PluginInstanceChild
 {
     memset(&mWindow, 0, sizeof(mWindow));
     mData.ndata = (void*) this;
 #if defined(MOZ_X11) && defined(XP_UNIX) && !defined(XP_MACOSX)
     mWindow.ws_info = &mWsInfo;
     memset(&mWsInfo, 0, sizeof(mWsInfo));
 #ifdef MOZ_WIDGET_GTK2
     mWsInfo.display = GDK_DISPLAY();
+#elif defined(MOZ_WIDGET_QT)
+    mWsInfo.display = QX11Info::display();
 #endif // MOZ_WIDGET_GTK2
 #endif // MOZ_X11 && XP_UNIX && !XP_MACOSX
 #if defined(OS_WIN)
     memset(&mAlphaExtract, 0, sizeof(mAlphaExtract));
     mAlphaExtract.doublePassEvent = ::RegisterWindowMessage(NS_OOPP_DOUBLEPASS_MSGID);
 #endif // OS_WIN
 }
 
--- a/dom/plugins/PluginInstanceParent.cpp
+++ b/dom/plugins/PluginInstanceParent.cpp
@@ -547,20 +547,18 @@ PluginInstanceParent::NPP_HandleEvent(vo
 
 #if defined(OS_WIN)
     if (mWindowType == NPWindowTypeDrawable) {
         switch(npevent->event) {
             case WM_PAINT:
             {
                 RECT rect;
                 SharedSurfaceBeforePaint(rect, npremoteevent);
-                if (!CallNPP_HandleEvent(npremoteevent, &handled))
-                    return 0;
-                if (handled)
-                    SharedSurfaceAfterPaint(npevent);
+                CallNPP_HandleEvent(npremoteevent, &handled);
+                SharedSurfaceAfterPaint(npevent);
             }
             break;
             default:
                 if (!CallNPP_HandleEvent(npremoteevent, &handled))
                     return 0;
             break;
         }
     }
@@ -578,16 +576,18 @@ PluginInstanceParent::NPP_HandleEvent(vo
         // drawing before the plugin draws on top.
         //
         // XSync() waits for the X server to complete.  Really this parent
         // process does not need to wait; the child is the process that needs
         // to wait.  A possibly-slightly-better alternative would be to send
         // an X event to the child that the child would wait for.
 #  ifdef MOZ_WIDGET_GTK2
         XSync(GDK_DISPLAY(), False);
+#  elif defined(MOZ_WIDGET_QT)
+        XSync(QX11Info::display(), False);
 #  endif
     }
 
     if (!CallNPP_HandleEvent(npremoteevent, &handled))
         return 0; // no good way to handle errors here...
 #endif
 
     return handled;
--- a/dom/plugins/PluginModuleChild.cpp
+++ b/dom/plugins/PluginModuleChild.cpp
@@ -32,16 +32,20 @@
  * use your version of this file under the terms of the MPL, indicate your
  * decision by deleting the provisions above and replace them with the notice
  * and other provisions required by the GPL or the LGPL. If you do not delete
  * the provisions above, a recipient may use your version of this file under
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 
+#ifdef MOZ_WIDGET_QT
+#include <QApplication>
+#endif
+
 #include "mozilla/plugins/PluginModuleChild.h"
 
 #ifdef MOZ_WIDGET_GTK2
 #include <gtk/gtk.h>
 #endif
 
 #include "nsILocalFile.h"
 
@@ -60,16 +64,19 @@
 #include "nsNPAPIPlugin.h"
 
 using mozilla::ipc::NPRemoteIdentifier;
 
 using namespace mozilla::plugins;
 
 namespace {
 PluginModuleChild* gInstance = nsnull;
+#ifdef MOZ_WIDGET_QT
+static QApplication *gQApp = nsnull;
+#endif
 }
 
 
 PluginModuleChild::PluginModuleChild() :
     mLibrary(0),
     mInitializeFunc(0),
     mShutdownFunc(0)
 #ifdef OS_WIN
@@ -84,16 +91,21 @@ PluginModuleChild::PluginModuleChild() :
 }
 
 PluginModuleChild::~PluginModuleChild()
 {
     NS_ASSERTION(gInstance == this, "Something terribly wrong here!");
     if (mLibrary) {
         PR_UnloadLibrary(mLibrary);
     }
+#ifdef MOZ_WIDGET_QT
+    if (gQApp)
+        delete gQApp;
+    gQApp = nsnull;
+#endif
     gInstance = nsnull;
 }
 
 // static
 PluginModuleChild*
 PluginModuleChild::current()
 {
     NS_ASSERTION(gInstance, "Null instance!");
@@ -254,16 +266,18 @@ PluginModuleChild::InitGraphics()
                       "InitGraphics called twice");
     real_gtk_plug_dispose = *dispose;
     *dispose = wrap_gtk_plug_dispose;
 
     GtkPlugEmbeddedFn* embedded = &GTK_PLUG_CLASS(gtk_plug_class)->embedded;
     real_gtk_plug_embedded = *embedded;
     *embedded = wrap_gtk_plug_embedded;
 #elif defined(MOZ_WIDGET_QT)
+    if (!qApp)
+        gQApp = new QApplication(0, NULL);
 #else
     // may not be necessary on all platforms
 #endif
 
     return true;
 }
 
 bool
--- a/dom/plugins/PluginModuleParent.cpp
+++ b/dom/plugins/PluginModuleParent.cpp
@@ -45,16 +45,34 @@
 using mozilla::PluginLibrary;
 
 using mozilla::ipc::NPRemoteIdentifier;
 
 using namespace mozilla::plugins;
 
 PR_STATIC_ASSERT(sizeof(NPIdentifier) == sizeof(void*));
 
+class PluginCrashed : public nsRunnable
+{
+public:
+    PluginCrashed(nsNPAPIPlugin* plugin,
+                  const nsString& dumpID)
+        : mDumpID(dumpID),
+          mPlugin(plugin) { }
+
+    NS_IMETHOD Run() {
+        mPlugin->PluginCrashed(mDumpID);
+        return NS_OK;
+    }
+
+private:
+    nsNPAPIPlugin* mPlugin;
+    nsString mDumpID;
+};
+
 // static
 PluginLibrary*
 PluginModuleParent::LoadModule(const char* aFilePath)
 {
     PLUGIN_LOG_DEBUG_FUNCTION;
 
     // Block on the child process being launched and initialized.
     PluginModuleParent* parent = new PluginModuleParent(aFilePath);
@@ -155,30 +173,34 @@ PluginModuleParent::WriteExtraDataForMin
 }
 
 void
 PluginModuleParent::ActorDestroy(ActorDestroyReason why)
 {
     switch (why) {
     case AbnormalShutdown: {
         nsCOMPtr<nsIFile> dump;
+        nsAutoString dumpID;
         if (GetMinidump(getter_AddRefs(dump))) {
             WriteExtraDataForMinidump(dump);
+            if (NS_SUCCEEDED(dump->GetLeafName(dumpID))) {
+                dumpID.Replace(dumpID.Length() - 4, 4,
+                               NS_LITERAL_STRING(""));
+            }
         }
         else {
             NS_WARNING("[PluginModuleParent::ActorDestroy] abnormal shutdown without minidump!");
         }
 
         mShutdown = true;
         // Defer the PluginCrashed method so that we don't re-enter
         // and potentially modify the actor child list while enumerating it.
         if (mPlugin) {
             nsCOMPtr<nsIRunnable> r =
-                new nsRunnableMethod<nsNPAPIPlugin>(
-                    mPlugin, &nsNPAPIPlugin::PluginCrashed);
+                new PluginCrashed(mPlugin, dumpID);
             NS_DispatchToMainThread(r);
         }
         break;
     }
     case NormalShutdown:
         mShutdown = true;
         break;
 
--- a/dom/src/geolocation/nsGeolocation.cpp
+++ b/dom/src/geolocation/nsGeolocation.cpp
@@ -361,17 +361,17 @@ nsresult nsGeolocationService::Init()
   mTimeout = nsContentUtils::GetIntPref("geo.timeout", 6000);
 
   nsContentUtils::RegisterPrefCallback("geo.enabled",
                                        GeoEnabledChangedCallback,
                                        nsnull);
 
   GeoEnabledChangedCallback("geo.enabled", nsnull);
 
-  if (sGeoEnabled == PR_FALSE)
+  if (!sGeoEnabled)
     return NS_ERROR_FAILURE;
 
   nsCOMPtr<nsIGeolocationProvider> provider = do_GetService(NS_GEOLOCATION_PROVIDER_CONTRACTID);
   if (provider)
     mProviders.AppendObject(provider);
 
   // look up any providers that were registered via the category manager
   nsCOMPtr<nsICategoryManager> catMan(do_GetService("@mozilla.org/categorymanager;1"));
@@ -575,17 +575,17 @@ PRBool
 nsGeolocationService::HasGeolocationProvider()
 {
   return mProviders.Count() > 0;
 }
 
 nsresult
 nsGeolocationService::StartDevice()
 {
-  if (sGeoEnabled == PR_FALSE)
+  if (!sGeoEnabled)
     return NS_ERROR_NOT_AVAILABLE;
 
   if (!HasGeolocationProvider())
     return NS_ERROR_NOT_AVAILABLE;
   
   // if we have one, start it up.
 
   // Start them up!
@@ -825,17 +825,17 @@ nsGeolocation::Update(nsIDOMGeoPosition 
 
 NS_IMETHODIMP
 nsGeolocation::GetCurrentPosition(nsIDOMGeoPositionCallback *callback,
                                   nsIDOMGeoPositionErrorCallback *errorCallback,
                                   nsIDOMGeoPositionOptions *options)
 {
   NS_ENSURE_ARG_POINTER(callback);
 
-  if (sGeoEnabled == PR_FALSE)
+  if (!sGeoEnabled)
     return NS_ERROR_NOT_AVAILABLE;
 
   if (mPendingCallbacks.Length() > MAX_GEO_REQUESTS_PER_WINDOW)
     return NS_ERROR_NOT_AVAILABLE;
 
   nsRefPtr<nsGeolocationRequest> request = new nsGeolocationRequest(this, callback, errorCallback, options);
   if (!request)
     return NS_ERROR_OUT_OF_MEMORY;
@@ -869,17 +869,17 @@ NS_IMETHODIMP
 nsGeolocation::WatchPosition(nsIDOMGeoPositionCallback *callback,
                              nsIDOMGeoPositionErrorCallback *errorCallback,
                              nsIDOMGeoPositionOptions *options,
                              PRInt32 *_retval NS_OUTPARAM)
 {
 
   NS_ENSURE_ARG_POINTER(callback);
 
-  if (sGeoEnabled == PR_FALSE)
+  if (!sGeoEnabled)
     return NS_ERROR_NOT_AVAILABLE;
 
   if (mPendingCallbacks.Length() > MAX_GEO_REQUESTS_PER_WINDOW)
     return NS_ERROR_NOT_AVAILABLE;
 
   nsRefPtr<nsGeolocationRequest> request = new nsGeolocationRequest(this, callback, errorCallback, options);
   if (!request)
     return NS_ERROR_OUT_OF_MEMORY;
--- a/dom/src/threads/nsDOMThreadService.cpp
+++ b/dom/src/threads/nsDOMThreadService.cpp
@@ -61,16 +61,17 @@
 
 // Other includes
 #include "jscntxt.h"
 #include "nsAutoLock.h"
 #include "nsAutoPtr.h"
 #include "nsContentUtils.h"
 #include "nsDeque.h"
 #include "nsIClassInfoImpl.h"
+#include "nsStringBuffer.h"
 #include "nsThreadUtils.h"
 #include "nsXPCOM.h"
 #include "nsXPCOMCID.h"
 #include "nsXPCOMCIDInternal.h"
 #include "pratom.h"
 #include "prthread.h"
 
 // DOMWorker includes
@@ -121,16 +122,26 @@ PRUintn gJSContextIndex = BAD_TLS_INDEX;
 
 static const char* sPrefsToWatch[] = {
   "dom.max_script_run_time"
 };
 
 // The length of time the close handler is allowed to run in milliseconds.
 static PRUint32 gWorkerCloseHandlerTimeoutMS = 10000;
 
+static int sStringFinalizerIndex = -1;
+
+static void
+StringFinalizer(JSContext* aCx,
+                JSString* aStr)
+{
+  NS_ASSERTION(aStr, "Null string!");
+  nsStringBuffer::FromData(JS_GetStringChars(aStr))->Release();
+}
+
 /**
  * Simple class to automatically destroy a JSContext to make error handling
  * easier.
  */
 class JSAutoContextDestroyer
 {
 public:
   JSAutoContextDestroyer(JSContext* aCx)
@@ -696,27 +707,31 @@ NS_IMPL_THREADSAFE_ISUPPORTS3(nsDOMThrea
                                                   nsIObserver,
                                                   nsIThreadPoolListener)
 
 nsresult
 nsDOMThreadService::Init()
 {
   NS_ASSERTION(NS_IsMainThread(), "Wrong thread!");
   NS_ASSERTION(!gDOMThreadService, "Only one instance should ever be created!");
+  NS_ASSERTION(sStringFinalizerIndex == -1, "String finalizer already set!");
 
   nsresult rv;
   nsCOMPtr<nsIObserverService> obs =
     do_GetService(NS_OBSERVERSERVICE_CONTRACTID, &rv);
   NS_ENSURE_SUCCESS(rv, rv);
 
   rv = obs->AddObserver(this, NS_XPCOM_SHUTDOWN_OBSERVER_ID, PR_FALSE);
   NS_ENSURE_SUCCESS(rv, rv);
 
   obs.forget(&gObserverService);
 
+  sStringFinalizerIndex = JS_AddExternalStringFinalizer(StringFinalizer);
+  NS_ENSURE_TRUE(sStringFinalizerIndex != -1, NS_ERROR_FAILURE);
+
   RegisterPrefCallbacks();
 
   mThreadPool = do_CreateInstance(NS_THREADPOOL_CONTRACTID, &rv);
   NS_ENSURE_SUCCESS(rv, rv);
 
   rv = mThreadPool->SetListener(this);
   NS_ENSURE_SUCCESS(rv, rv);
 
@@ -853,16 +868,25 @@ nsDOMThreadService::Cleanup()
       JS_GC(safeContext);
     }
     NS_RELEASE(gThreadJSContextStack);
   }
 
   // These must be released after the thread pool is shut down.
   NS_IF_RELEASE(gJSRuntimeService);
   NS_IF_RELEASE(gWorkerSecurityManager);
+
+  if (sStringFinalizerIndex != -1) {
+#ifdef DEBUG
+    int index =
+#endif
+    JS_RemoveExternalStringFinalizer(StringFinalizer);
+    NS_ASSERTION(index == sStringFinalizerIndex, "Bad index!");
+    sStringFinalizerIndex = -1;
+  }
 }
 
 nsresult
 nsDOMThreadService::Dispatch(nsDOMWorker* aWorker,
                              nsIRunnable* aRunnable,
                              PRIntervalTime aTimeoutInterval,
                              PRBool aClearQueue)
 {
@@ -1200,34 +1224,69 @@ nsDOMThreadService::ChangeThreadPoolMaxT
       rv = mThreadPool->Dispatch(dummy, NS_DISPATCH_NORMAL);
       NS_ENSURE_SUCCESS(rv, rv);
     }
   }
 
   return NS_OK;
 }
 
+// static
 nsIJSRuntimeService*
 nsDOMThreadService::JSRuntimeService()
 {
   return gJSRuntimeService;
 }
 
+// static
 nsIThreadJSContextStack*
 nsDOMThreadService::ThreadJSContextStack()
 {
   return gThreadJSContextStack;
 }
 
+// static
 nsIXPCSecurityManager*
 nsDOMThreadService::WorkerSecurityManager()
 {
   return gWorkerSecurityManager;
 }
 
+// static
+jsval
+nsDOMThreadService::ShareStringAsJSVal(JSContext* aCx,
+                                       const nsAString& aString)
+{
+  NS_ASSERTION(sStringFinalizerIndex != -1, "Bad index!");
+  NS_ASSERTION(aCx, "Null context!");
+
+  PRUint32 length = aString.Length();
+  if (!length) {
+    JSAtom* atom = aCx->runtime->atomState.emptyAtom;
+    return ATOM_KEY(atom);
+  }
+
+  nsStringBuffer* buf = nsStringBuffer::FromString(aString);
+  if (!buf) {
+    NS_WARNING("Can't share this string buffer!");
+    return JSVAL_VOID;
+  }
+
+  JSString* str =
+    JS_NewExternalString(aCx, reinterpret_cast<jschar*>(buf->Data()), length,
+                         sStringFinalizerIndex);
+  if (str) {
+    buf->AddRef();
+    return STRING_TO_JSVAL(str);
+  }
+
+  NS_WARNING("JS_NewExternalString failed!");
+  return JSVAL_VOID;
+}
+
 /**
  * See nsIEventTarget
  */
 NS_IMETHODIMP
 nsDOMThreadService::Dispatch(nsIRunnable* aEvent,
                              PRUint32 aFlags)
 {
   NS_ENSURE_ARG_POINTER(aEvent);
--- a/dom/src/threads/nsDOMThreadService.h
+++ b/dom/src/threads/nsDOMThreadService.h
@@ -103,16 +103,19 @@ public:
 
   static JSContext* GetCurrentContext();
 
   // Easy access to the services we care about.
   static nsIJSRuntimeService* JSRuntimeService();
   static nsIThreadJSContextStack* ThreadJSContextStack();
   static nsIXPCSecurityManager* WorkerSecurityManager();
 
+  static jsval ShareStringAsJSVal(JSContext* aCx,
+                                  const nsAString& aString);
+
   void CancelWorkersForGlobal(nsIScriptGlobalObject* aGlobalObject);
   void SuspendWorkersForGlobal(nsIScriptGlobalObject* aGlobalObject);
   void ResumeWorkersForGlobal(nsIScriptGlobalObject* aGlobalObject);
 
   nsresult ChangeThreadPoolMaxThreads(PRInt16 aDelta);
 
 private:
   nsDOMThreadService();
--- a/dom/src/threads/nsDOMWorker.cpp
+++ b/dom/src/threads/nsDOMWorker.cpp
@@ -408,108 +408,96 @@ WriteCallback(const jschar* aBuffer,
 {
   nsJSONWriter* writer = static_cast<nsJSONWriter*>(aData);
 
   nsresult rv = writer->Write((const PRUnichar*)aBuffer, (PRUint32)aLength);
   return NS_SUCCEEDED(rv) ? JS_TRUE : JS_FALSE;
 }
 
 static nsresult
-GetStringForArgument(nsAString& aString,
+GetStringForArgument(JSContext* aCx,
+                     jsval aVal,
                      PRBool* aIsJSON,
-                     PRBool* aIsPrimitive)
+                     PRBool* aIsPrimitive,
+                     nsAutoJSValHolder& _retval)
 {
   NS_ASSERTION(aIsJSON && aIsPrimitive, "Null pointer!");
 
-  nsIXPConnect* xpc = nsContentUtils::XPConnect();
-  NS_ENSURE_TRUE(xpc, NS_ERROR_UNEXPECTED);
-
-  nsAXPCNativeCallContext* cc;
-  nsresult rv = xpc->GetCurrentNativeCallContext(&cc);
-  NS_ENSURE_SUCCESS(rv, rv);
-  NS_ENSURE_TRUE(cc, NS_ERROR_UNEXPECTED);
-
-  PRUint32 argc;
-  rv = cc->GetArgc(&argc);
-  NS_ENSURE_SUCCESS(rv, rv);
-
-  if (!argc) {
-    return NS_ERROR_XPC_NOT_ENOUGH_ARGS;
-  }
-
-  jsval* argv;
-  rv = cc->GetArgvPtr(&argv);
-  NS_ENSURE_SUCCESS(rv, rv);
-
-  JSContext* cx;
-  rv = cc->GetJSContext(&cx);
-  NS_ENSURE_SUCCESS(rv, rv);
-
-  JSAutoRequest ar(cx);
-
-  if (JSVAL_IS_STRING(argv[0])) {
-    aString.Assign(nsDependentJSString(JSVAL_TO_STRING(argv[0])));
+  if (JSVAL_IS_STRING(aVal)) {
     *aIsJSON = *aIsPrimitive = PR_FALSE;
+    _retval = aVal;
     return NS_OK;
   }
 
   nsAutoJSValHolder jsonVal;
 
-  JSBool ok = jsonVal.Hold(cx);
+  JSBool ok = jsonVal.Hold(aCx);
   NS_ENSURE_TRUE(ok, NS_ERROR_FAILURE);
 
-  if (JSVAL_IS_PRIMITIVE(argv[0])) {
+  if (JSVAL_IS_PRIMITIVE(aVal)) {
     // Only objects can be serialized through JSON, currently, so if we've been
     // given a primitive we set it as a property on a dummy object before
     // sending it to the serializer.
-    JSObject* obj = JS_NewObject(cx, NULL, NULL, NULL);
+    JSObject* obj = JS_NewObject(aCx, NULL, NULL, NULL);
     NS_ENSURE_TRUE(obj, NS_ERROR_OUT_OF_MEMORY);
 
     jsonVal = obj;
 
-    ok = JS_DefineProperty(cx, obj, JSON_PRIMITIVE_PROPNAME, argv[0], NULL,
+    ok = JS_DefineProperty(aCx, obj, JSON_PRIMITIVE_PROPNAME, aVal, NULL,
                            NULL, JSPROP_ENUMERATE);
     NS_ENSURE_TRUE(ok, NS_ERROR_UNEXPECTED);
 
     *aIsPrimitive = PR_TRUE;
   }
   else {
-    jsonVal = argv[0];
+    jsonVal = aVal;
 
     *aIsPrimitive = PR_FALSE;
   }
 
   JSType type;
   jsval* vp = jsonVal.ToJSValPtr();
 
   // This may change vp if there is a 'toJSON' function on the object.
-  ok = JS_TryJSON(cx, vp);
+  ok = JS_TryJSON(aCx, vp);
   if (!(ok && !JSVAL_IS_PRIMITIVE(*vp) &&
-        (type = JS_TypeOfValue(cx, *vp)) != JSTYPE_FUNCTION &&
+        (type = JS_TypeOfValue(aCx, *vp)) != JSTYPE_FUNCTION &&
         type != JSTYPE_XML)) {
     return NS_ERROR_INVALID_ARG;
   }
 
   // Make sure to hold the new vp in case it changed.
   jsonVal = *vp;
 
   nsJSONWriter writer;
 
-  ok = JS_Stringify(cx, jsonVal.ToJSValPtr(), NULL, JSVAL_NULL, WriteCallback, &writer);
+  ok = JS_Stringify(aCx, jsonVal.ToJSValPtr(), NULL, JSVAL_NULL, WriteCallback,
+                    &writer);
   if (!ok) {
     return NS_ERROR_XPC_BAD_CONVERT_JS;
   }
 
   NS_ENSURE_TRUE(writer.DidWrite(), NS_ERROR_UNEXPECTED);
 
   writer.FlushBuffer();
 
-  aString.Assign(writer.mOutputString);
+  _retval = nsDOMThreadService::ShareStringAsJSVal(aCx, writer.mOutputString);
+  if (!JSVAL_IS_STRING(_retval)) {
+    // Yuck, we can't share.
+    const jschar* buf =
+      reinterpret_cast<const jschar*>(writer.mOutputString.get());
+    JSString* str = JS_NewUCStringCopyN(aCx, buf, writer.mOutputString.Length());
+    if (!str) {
+      JS_ReportOutOfMemory(aCx);
+      return NS_ERROR_OUT_OF_MEMORY;
+    }
+    _retval = STRING_TO_JSVAL(str);
+  }
+
   *aIsJSON = PR_TRUE;
-
   return NS_OK;
 }
 
 nsDOMWorkerScope::nsDOMWorkerScope(nsDOMWorker* aWorker)
 : mWorker(aWorker),
   mWrappedNative(nsnull),
   mHasOnerror(PR_FALSE)
 {
@@ -750,23 +738,17 @@ NS_IMETHODIMP
 nsDOMWorkerScope::PostMessage(/* JSObject aMessage */)
 {
   NS_ASSERTION(!NS_IsMainThread(), "Wrong thread!");
 
   if (mWorker->IsCanceled()) {
     return NS_ERROR_ABORT;
   }
 
-  nsString message;
-  PRBool isJSON, isPrimitive;
-
-  nsresult rv = GetStringForArgument(message, &isJSON, &isPrimitive);
-  NS_ENSURE_SUCCESS(rv, rv);
-
-  return mWorker->PostMessageInternal(message, isJSON, isPrimitive, PR_FALSE);
+  return mWorker->PostMessageInternal(PR_FALSE);
 }
 
 NS_IMETHODIMP
 nsDOMWorkerScope::Close()
 {
   NS_ASSERTION(!NS_IsMainThread(), "Wrong thread!");
 
   return mWorker->Close();
@@ -1450,30 +1432,65 @@ nsDOMWorker::IsClosing()
 PRBool
 nsDOMWorker::IsSuspended()
 {
   nsAutoLock lock(mLock);
   return mSuspended;
 }
 
 nsresult
-nsDOMWorker::PostMessageInternal(const nsAString& aMessage,
-                                 PRBool aIsJSON,
-                                 PRBool aIsPrimitive,
-                                 PRBool aToInner)
+nsDOMWorker::PostMessageInternal(PRBool aToInner)
 {
+  nsIXPConnect* xpc = nsContentUtils::XPConnect();
+  NS_ENSURE_TRUE(xpc, NS_ERROR_UNEXPECTED);
+
+  nsAXPCNativeCallContext* cc;
+  nsresult rv = xpc->GetCurrentNativeCallContext(&cc);
+  NS_ENSURE_SUCCESS(rv, rv);
+  NS_ENSURE_TRUE(cc, NS_ERROR_UNEXPECTED);
+
+  PRUint32 argc;
+  rv = cc->GetArgc(&argc);
+  NS_ENSURE_SUCCESS(rv, rv);
+
+  if (!argc) {
+    return NS_ERROR_XPC_NOT_ENOUGH_ARGS;
+  }
+
+  jsval* argv;
+  rv = cc->GetArgvPtr(&argv);
+  NS_ENSURE_SUCCESS(rv, rv);
+
+  JSContext* cx;
+  rv = cc->GetJSContext(&cx);
+  NS_ENSURE_SUCCESS(rv, rv);
+
+  JSAutoRequest ar(cx);
+
+  nsAutoJSValHolder val;
+  if (!val.Hold(cx)) {
+    return NS_ERROR_FAILURE;
+  }
+
+  PRBool isJSON, isPrimitive;
+  rv = GetStringForArgument(cx, argv[0], &isJSON, &isPrimitive, val);
+  NS_ENSURE_SUCCESS(rv, rv);
+
+  NS_ASSERTION(JSVAL_IS_STRING(val), "Bad jsval!");
+
   nsRefPtr<nsDOMWorkerMessageEvent> message = new nsDOMWorkerMessageEvent();
   NS_ENSURE_TRUE(message, NS_ERROR_OUT_OF_MEMORY);
 
-  nsresult rv = message->InitMessageEvent(NS_LITERAL_STRING("message"),
-                                          PR_FALSE, PR_FALSE, aMessage,
-                                          EmptyString(), nsnull);
+  rv = message->InitMessageEvent(NS_LITERAL_STRING("message"), PR_FALSE,
+                                 PR_FALSE, EmptyString(), EmptyString(),
+                                 nsnull);
   NS_ENSURE_SUCCESS(rv, rv);
 
-  message->SetJSONData(aIsJSON, aIsPrimitive);
+  rv = message->SetJSONData(cx, val, isJSON, isPrimitive);
+  NS_ENSURE_SUCCESS(rv, rv);
 
   nsRefPtr<nsDOMFireEventRunnable> runnable =
     new nsDOMFireEventRunnable(this, message, aToInner);
   NS_ENSURE_TRUE(runnable, NS_ERROR_OUT_OF_MEMORY);
 
   // If aToInner is true then we want to target the runnable at this worker's
   // thread. Otherwise we need to target the parent's thread.
   nsDOMWorker* target = aToInner ? this : mParent;
@@ -1973,23 +1990,17 @@ nsDOMWorker::PostMessage(/* JSObject aMe
     nsAutoLock lock(mLock);
     // There's no reason to dispatch this message after the close handler has
     // been triggered since it will never be allowed to run.
     if (mStatus != eRunning) {
       return NS_OK;
     }
   }
 
-  nsString message;
-  PRBool isJSON, isPrimitive;
-
-  nsresult rv = GetStringForArgument(message, &isJSON, &isPrimitive);
-  NS_ENSURE_SUCCESS(rv, rv);
-
-  return PostMessageInternal(message, isJSON, isPrimitive, PR_TRUE);
+  return PostMessageInternal(PR_TRUE);
 }
 
 /**
  * See nsIWorker
  */
 NS_IMETHODIMP
 nsDOMWorker::GetOnerror(nsIDOMEventListener** aOnerror)
 {
--- a/dom/src/threads/nsDOMWorker.h
+++ b/dom/src/threads/nsDOMWorker.h
@@ -242,20 +242,17 @@ public:
 
     // The close handler has run and the worker is effectively dead.
     eKilled
   };
 
 private:
   ~nsDOMWorker();
 
-  nsresult PostMessageInternal(const nsAString& aMessage,
-                               PRBool aIsJSON,
-                               PRBool aIsPrimitive,
-                               PRBool aToInner);
+  nsresult PostMessageInternal(PRBool aToInner);
 
   PRBool CompileGlobalObject(JSContext* aCx);
 
   PRUint32 NextTimeoutId() {
     return ++mNextTimeoutId;
   }
 
   nsresult AddFeature(nsDOMWorkerFeature* aFeature,
--- a/dom/src/threads/nsDOMWorkerEvents.cpp
+++ b/dom/src/threads/nsDOMWorkerEvents.cpp
@@ -258,36 +258,57 @@ nsDOMWorkerEvent::InitEvent(const nsAStr
 NS_IMPL_ISUPPORTS_INHERITED1(nsDOMWorkerMessageEvent, nsDOMWorkerEvent,
                                                       nsIWorkerMessageEvent)
 
 NS_IMPL_CI_INTERFACE_GETTER2(nsDOMWorkerMessageEvent, nsIDOMEvent,
                                                       nsIWorkerMessageEvent)
 
 NS_IMPL_THREADSAFE_DOM_CI_GETINTERFACES(nsDOMWorkerMessageEvent)
 
+nsresult
+nsDOMWorkerMessageEvent::SetJSONData(JSContext* aCx,
+                                     jsval aData,
+                                     PRBool aIsJSON,
+                                     PRBool aIsPrimitive)
+{
+  NS_ASSERTION(JSVAL_IS_STRING(aData), "Bad jsval!");
+
+  mIsJSON = aIsJSON ? PR_TRUE : PR_FALSE;
+  mIsPrimitive = aIsPrimitive ? PR_TRUE : PR_FALSE;
+
+  if (!mDataVal.Hold(aCx)) {
+    NS_WARNING("Failed to hold jsval!");
+    return NS_ERROR_FAILURE;
+  }
+
+  mDataVal = aData;
+  return NS_OK;
+}
+
 NS_IMETHODIMP
 nsDOMWorkerMessageEvent::GetData(nsAString& aData)
 {
-  if (!mIsJSON) {
-    aData.Assign(mData);
-    return NS_OK;
-  }
-
   nsIXPConnect* xpc = nsContentUtils::XPConnect();
   NS_ENSURE_TRUE(xpc, NS_ERROR_UNEXPECTED);
 
   nsAXPCNativeCallContext* cc;
   nsresult rv = xpc->GetCurrentNativeCallContext(&cc);
   NS_ENSURE_SUCCESS(rv, rv);
   NS_ENSURE_TRUE(cc, NS_ERROR_UNEXPECTED);
 
   jsval* retval;
   rv = cc->GetRetValPtr(&retval);
   NS_ENSURE_SUCCESS(rv, rv);
 
+  if (!mIsJSON) {
+    cc->SetReturnValueWasSet(PR_TRUE);
+    *retval = mDataVal;
+    return NS_OK;
+  }
+
   if (mHaveCachedJSVal) {
     cc->SetReturnValueWasSet(PR_TRUE);
     *retval = mCachedJSVal;
     return NS_OK;
   }
 
   if (mHaveAttemptedConversion) {
     // Don't try to convert again if the first time around we saw an error.
@@ -299,24 +320,27 @@ nsDOMWorkerMessageEvent::GetData(nsAStri
   rv = cc->GetJSContext(&cx);
   NS_ENSURE_SUCCESS(rv, rv);
 
   JSAutoRequest ar(cx);
 
   JSBool ok = mCachedJSVal.Hold(cx);
   NS_ENSURE_TRUE(ok, NS_ERROR_FAILURE);
 
+  NS_ASSERTION(JSVAL_IS_STRING(mDataVal), "Bad jsval!");
+  JSString* str = JSVAL_TO_STRING(mDataVal);
+
   JSONParser* parser = JS_BeginJSONParse(cx, mCachedJSVal.ToJSValPtr());
   NS_ENSURE_TRUE(parser, NS_ERROR_UNEXPECTED);
 
   // This is slightly sneaky, but now that JS_BeginJSONParse succeeded we always
   // need call JS_FinishJSONParse even if JS_ConsumeJSONText fails. We'll report
   // an error if either failed, though.
-  ok = JS_ConsumeJSONText(cx, parser, (jschar*)mData.get(),
-                          (uint32)mData.Length());
+  ok = JS_ConsumeJSONText(cx, parser, JS_GetStringChars(str),
+                          JS_GetStringLength(str));
 
   // Note the '&& ok' after the call here!
   ok = JS_FinishJSONParse(cx, parser, JSVAL_NULL) && ok;
   if (!ok) {
     mCachedJSVal = JSVAL_NULL;
     return NS_ERROR_UNEXPECTED;
   }
 
@@ -331,17 +355,17 @@ nsDOMWorkerMessageEvent::GetData(nsAStri
       mCachedJSVal = JSVAL_NULL;
       return NS_ERROR_UNEXPECTED;
     }
 
     mCachedJSVal = primitive;
   }
 
   // We no longer need to hold this copy of the data around.
-  mData.Truncate();
+  mDataVal.Release();
 
   // Now that everything has succeeded we'll set this flag so that we return the
   // cached jsval in the future.
   mHaveCachedJSVal = PR_TRUE;
 
   *retval = mCachedJSVal;
   cc->SetReturnValueWasSet(PR_TRUE);
   return NS_OK;
@@ -365,17 +389,16 @@ nsDOMWorkerMessageEvent::GetSource(nsISu
 NS_IMETHODIMP
 nsDOMWorkerMessageEvent::InitMessageEvent(const nsAString& aTypeArg,
                                           PRBool aCanBubbleArg,
                                           PRBool aCancelableArg,
                                           const nsAString& aDataArg,
                                           const nsAString& aOriginArg,
                                           nsISupports* aSourceArg)
 {
-  mData.Assign(aDataArg);
   mOrigin.Assign(aOriginArg);
   mSource = aSourceArg;
   return nsDOMWorkerEvent::InitEvent(aTypeArg, aCanBubbleArg, aCancelableArg);
 }
 
 NS_IMPL_ISUPPORTS_INHERITED1(nsDOMWorkerProgressEvent, nsDOMWorkerEvent,
                                                        nsIDOMProgressEvent)
 
--- a/dom/src/threads/nsDOMWorkerEvents.h
+++ b/dom/src/threads/nsDOMWorkerEvents.h
@@ -209,26 +209,26 @@ public:
   NS_FORWARD_NSIDOMEVENT(nsDOMWorkerEvent::)
   NS_DECL_NSIWORKERMESSAGEEVENT
   NS_DECL_NSICLASSINFO_GETINTERFACES
 
   nsDOMWorkerMessageEvent()
   : mIsJSON(PR_FALSE), mIsPrimitive(PR_FALSE), mHaveCachedJSVal(PR_FALSE),
     mHaveAttemptedConversion(PR_FALSE) { }
 
-  void SetJSONData(PRBool aIsJSON, PRBool aIsPrimitive) {
-    mIsJSON = aIsJSON ? PR_TRUE : PR_FALSE;
-    mIsPrimitive = aIsPrimitive ? PR_TRUE : PR_FALSE;
-  }
+  nsresult SetJSONData(JSContext* aCx,
+                       jsval aData,
+                       PRBool aIsJSON,
+                       PRBool aIsPrimitive);
 
 protected:
   nsString mOrigin;
   nsCOMPtr<nsISupports> mSource;
 
-  nsString mData;
+  nsAutoJSValHolder mDataVal;
   nsAutoJSValHolder mCachedJSVal;
 
   PRPackedBool mIsJSON;
   PRPackedBool mIsPrimitive;
   PRPackedBool mHaveCachedJSVal;
   PRPackedBool mHaveAttemptedConversion;
 };
 
--- a/gfx/cairo/libpixman/src/Makefile.in
+++ b/gfx/cairo/libpixman/src/Makefile.in
@@ -87,18 +87,17 @@ ifneq ($(MOZ_WIDGET_TOOLKIT),os2)
 MMX_CFLAGS+=--param inline-unit-growth=10000 --param large-function-growth=10000
 endif
 endif
 ifeq (arm,$(findstring arm,$(OS_TEST)))
 ifdef HAVE_ARM_SIMD
 USE_ARM_SIMD_GCC=1
 endif
 ifdef HAVE_ARM_NEON
-# temporarily disabled to see if it fixes odd mobile build breakage
-#USE_ARM_NEON_GCC=1
+USE_ARM_NEON_GCC=1
 endif
 endif
 
 endif
 
 
 CSRCS	= \
 	pixman-access.c \
@@ -143,16 +142,17 @@ endif
 
 ifdef USE_ARM_SIMD_GCC
 CSRCS += pixman-arm-simd.c pixman-arm-simd-asm.c
 DEFINES += -DUSE_ARM_SIMD
 endif
 
 ifdef USE_ARM_NEON_GCC
 CSRCS += pixman-arm-neon.c
+SSRCS += pixman-arm-neon-asm.S
 DEFINES += -DUSE_ARM_NEON
 ARM_NEON_CFLAGS = -mfloat-abi=softfp -mfpu=neon
 endif
 
 ifdef USE_ARM_SIMD_MSVC
 ASFILES += pixman-arm-detect-win32.asm pixman-wce-arm-simd.asm
 CSRCS += pixman-arm-simd.c
 DEFINES += -DUSE_ARM_SIMD
--- a/gfx/cairo/libpixman/src/pixman-arm-neon-asm.S
+++ b/gfx/cairo/libpixman/src/pixman-arm-neon-asm.S
@@ -812,18 +812,18 @@ generate_composite_function \
 .endm
 
 .macro pixman_composite_src_n_8_init
     add         DUMMY, sp, #ARGS_STACK_OFFSET
     vld1.32     {d0[0]}, [DUMMY]
     vsli.u64    d0, d0, #8
     vsli.u64    d0, d0, #16
     vsli.u64    d0, d0, #32
-    vmov        d1, d0
-    vmov        q1, q0
+    vorr        d1, d0, d0
+    vorr        q1, q0, q0
 .endm
 
 .macro pixman_composite_src_n_8_cleanup
 .endm
 
 generate_composite_function \
     pixman_composite_src_n_8_asm_neon, 0, 0, 8, \
     FLAG_DST_WRITEONLY, \
@@ -851,18 +851,18 @@ generate_composite_function \
     vst1.16 {d0, d1, d2, d3}, [DST_W, :128]!
 .endm
 
 .macro pixman_composite_src_n_0565_init
     add         DUMMY, sp, #ARGS_STACK_OFFSET
     vld1.32     {d0[0]}, [DUMMY]
     vsli.u64    d0, d0, #16
     vsli.u64    d0, d0, #32
-    vmov        d1, d0
-    vmov        q1, q0
+    vorr        d1, d0, d0
+    vorr        q1, q0, q0
 .endm
 
 .macro pixman_composite_src_n_0565_cleanup
 .endm
 
 generate_composite_function \
     pixman_composite_src_n_0565_asm_neon, 0, 0, 16, \
     FLAG_DST_WRITEONLY, \
@@ -889,18 +889,18 @@ generate_composite_function \
 .macro pixman_composite_src_n_8888_process_pixblock_tail_head
     vst1.32 {d0, d1, d2, d3}, [DST_W, :128]!
 .endm
 
 .macro pixman_composite_src_n_8888_init
     add         DUMMY, sp, #ARGS_STACK_OFFSET
     vld1.32     {d0[0]}, [DUMMY]
     vsli.u64    d0, d0, #32
-    vmov        d1, d0
-    vmov        q1, q0
+    vorr        d1, d0, d0
+    vorr        q1, q0, q0
 .endm
 
 .macro pixman_composite_src_n_8888_cleanup
 .endm
 
 generate_composite_function \
     pixman_composite_src_n_8888_asm_neon, 0, 0, 32, \
     FLAG_DST_WRITEONLY, \
--- a/intl/chardet/src/nsDebugDetector.cpp
+++ b/intl/chardet/src/nsDebugDetector.cpp
@@ -66,17 +66,17 @@ NS_IMETHODIMP nsDebugDetector::Init(nsIC
   mObserver = aObserver;
   return NS_OK;
 }
 //--------------------------------------------------------------------
 
 NS_IMETHODIMP nsDebugDetector::DoIt(const char* aBytesArray, PRUint32 aLen, PRBool* oDontFeedMe)
 {
   NS_ASSERTION(mObserver != nsnull , "have not init yet");
-  NS_ASSERTION(mStop == PR_FALSE , "don't call DoIt if we return PR_TRUE in oDontFeedMe");
+  NS_ASSERTION(!mStop , "don't call DoIt if we return PR_TRUE in oDontFeedMe");
 
   if((nsnull == aBytesArray) || (nsnull == oDontFeedMe))
      return NS_ERROR_ILLEGAL_VALUE;
 
   mBlks++;
   if((k1stBlk == mSel) && (1 == mBlks)) {
      *oDontFeedMe = mStop = PR_TRUE;
      Report();
--- a/intl/chardet/src/nsMetaCharsetObserver.cpp
+++ b/intl/chardet/src/nsMetaCharsetObserver.cpp
@@ -397,17 +397,17 @@ NS_IMETHODIMP nsMetaCharsetObserver::Obs
   return rv;
 }
 
 //-------------------------------------------------------------------------
 NS_IMETHODIMP nsMetaCharsetObserver::Start() 
 {
   nsresult rv = NS_OK;
 
-  if (bMetaCharsetObserverStarted == PR_FALSE)  {
+  if (!bMetaCharsetObserverStarted)  {
     bMetaCharsetObserverStarted = PR_TRUE;
 
     nsCOMPtr<nsIParserService> parserService(do_GetService(NS_PARSERSERVICE_CONTRACTID, &rv));
 
     if (NS_FAILED(rv))
       return rv;
 
     rv = parserService->RegisterObserver(this,
@@ -416,17 +416,17 @@ NS_IMETHODIMP nsMetaCharsetObserver::Sta
   }
 
   return rv;
 }
 //-------------------------------------------------------------------------
 NS_IMETHODIMP nsMetaCharsetObserver::End() 
 {
   nsresult rv = NS_OK;
-  if (bMetaCharsetObserverStarted == PR_TRUE)  {
+  if (bMetaCharsetObserverStarted)  {
     bMetaCharsetObserverStarted = PR_FALSE;
 
     nsCOMPtr<nsIParserService> parserService(do_GetService(NS_PARSERSERVICE_CONTRACTID, &rv));
 
     if (NS_FAILED(rv))
       return rv;
     
     rv = parserService->UnregisterObserver(this, NS_LITERAL_STRING("text/html"));
--- a/intl/chardet/src/nsXMLEncodingObserver.cpp
+++ b/intl/chardet/src/nsXMLEncodingObserver.cpp
@@ -63,17 +63,17 @@ static const eHTMLTags gTags[] =
 nsXMLEncodingObserver::nsXMLEncodingObserver()
 {
   bXMLEncodingObserverStarted = PR_FALSE;
 }
 //-------------------------------------------------------------------------
 nsXMLEncodingObserver::~nsXMLEncodingObserver()
 {
   // call to end the ObserverService
-  if (bXMLEncodingObserverStarted == PR_TRUE) {
+  if (bXMLEncodingObserverStarted) {
     End();
   }
 }
 
 //-------------------------------------------------------------------------
 NS_IMPL_ADDREF ( nsXMLEncodingObserver )
 NS_IMPL_RELEASE ( nsXMLEncodingObserver )
 
@@ -195,17 +195,17 @@ NS_IMETHODIMP nsXMLEncodingObserver::Obs
 {
     return NS_ERROR_NOT_IMPLEMENTED;
 }
 //-------------------------------------------------------------------------
 NS_IMETHODIMP nsXMLEncodingObserver::Start() 
 {
     nsresult res = NS_OK;
 
-    if (bXMLEncodingObserverStarted == PR_TRUE) 
+    if (bXMLEncodingObserverStarted) 
       return res;
 
     nsCOMPtr<nsIObserverService> anObserverService = do_GetService("@mozilla.org/observer-service;1", &res);
 
     if (NS_SUCCEEDED(res)) {
       res = anObserverService->AddObserver(this, "xmlparser", PR_TRUE);
 
       bXMLEncodingObserverStarted = PR_TRUE;
@@ -213,17 +213,17 @@ NS_IMETHODIMP nsXMLEncodingObserver::Sta
 
     return res;
 }
 //-------------------------------------------------------------------------
 NS_IMETHODIMP nsXMLEncodingObserver::End() 
 {
     nsresult res = NS_OK;
     
-    if (bXMLEncodingObserverStarted == PR_FALSE) 
+    if (!bXMLEncodingObserverStarted)
       return res;
 
     nsCOMPtr<nsIObserverService> anObserverService = do_GetService("@mozilla.org/observer-service;1", &res);
     if (NS_SUCCEEDED(res)) {
       res = anObserverService->RemoveObserver(this, "xmlparser");
 
       bXMLEncodingObserverStarted = PR_FALSE;
     }
--- a/js/src/config/rules.mk
+++ b/js/src/config/rules.mk
@@ -375,16 +375,17 @@ ifndef TARGETS
 TARGETS			= $(LIBRARY) $(SHARED_LIBRARY) $(PROGRAM) $(SIMPLE_PROGRAMS) $(HOST_LIBRARY) $(HOST_PROGRAM) $(HOST_SIMPLE_PROGRAMS) $(JAVA_LIBRARY)
 endif
 
 ifndef OBJS
 _OBJS			= \
 	$(JRI_STUB_CFILES) \
 	$(addsuffix .$(OBJ_SUFFIX), $(JMC_GEN)) \
 	$(CSRCS:.c=.$(OBJ_SUFFIX)) \
+	$(SSRCS:.S=.$(OBJ_SUFFIX)) \
 	$(patsubst %.cc,%.$(OBJ_SUFFIX),$(CPPSRCS:.cpp=.$(OBJ_SUFFIX))) \
 	$(CMSRCS:.m=.$(OBJ_SUFFIX)) \
 	$(CMMSRCS:.mm=.$(OBJ_SUFFIX)) \
 	$(ASFILES:.$(ASM_SUFFIX)=.$(OBJ_SUFFIX))
 OBJS	= $(strip $(_OBJS))
 endif
 
 ifndef HOST_OBJS
--- a/js/src/config/system-headers
+++ b/js/src/config/system-headers
@@ -1004,22 +1004,20 @@ libsn/sn-monitor.h
 libsn/sn-util.h
 #endif
 #if MOZ_NATIVE_HUNSPELL==1
 hunspell.hxx
 #endif
 #if MOZ_NATIVE_BZ2==1
 bzlib.h
 #endif
-#ifdef MOZ_PLATFORM_HILDON
+#if MOZ_PLATFORM_MAEMO==5
 hildon-uri.h
 hildon-mime.h
 hildon-file-chooser-dialog.h
-#endif
-#ifdef NS_OSSO
 libosso.h
 osso-mem.h
 #endif
 #ifdef MOZ_ENABLE_GIO
 gio/gio.h
 #endif
 #ifdef MOZ_ENABLE_LIBCONIC
 conic/conicconnection.h
--- a/js/src/configure.in
+++ b/js/src/configure.in
@@ -353,38 +353,38 @@ else
     AC_PROG_CXX
     AC_PROG_RANLIB
     MOZ_PATH_PROGS(AS, $AS as, $CC)
     AC_CHECK_PROGS(AR, ar, :)
     AC_CHECK_PROGS(LD, ld, :)
     AC_CHECK_PROGS(STRIP, strip, :)
     AC_CHECK_PROGS(WINDRES, windres, :)
     if test -z "$HOST_CC"; then
-        HOST_CC="$CC"
+        HOST_CC='$(CC)'
     fi
     if test -z "$HOST_CFLAGS"; then
-        HOST_CFLAGS="$CFLAGS"
+        HOST_CFLAGS='$(CFLAGS)'
     fi
     if test -z "$HOST_CXX"; then
-        HOST_CXX="$CXX"
+        HOST_CXX='$(CXX)'
     fi
     if test -z "$HOST_CXXFLAGS"; then
-        HOST_CXXFLAGS="$CXXFLAGS"
+        HOST_CXXFLAGS='$(CXXFLAGS)'
     fi
     if test -z "$HOST_LDFLAGS"; then
-        HOST_LDFLAGS="$LDFLAGS"
+        HOST_LDFLAGS='$(LDFLAGS)'
     fi
     if test -z "$HOST_RANLIB"; then
-        HOST_RANLIB="$RANLIB"
+        HOST_RANLIB='$(RANLIB)'
     fi
     if test -z "$HOST_AR"; then
-        HOST_AR="$AR"
+        HOST_AR='$(AR)'
     fi
     if test -z "$HOST_AR_FLAGS"; then
-        HOST_AR_FLAGS="$AR_FLAGS"
+        HOST_AR_FLAGS='$(AR_FLAGS)'
     fi
 fi
 
 GNU_AS=
 GNU_LD=
 GNU_CC=
 GNU_CXX=
 CC_VERSION='N/A'
@@ -1503,18 +1503,18 @@ case "$host" in
         ;;
     esac
     ;;
 
 *-darwin*)
     HOST_CFLAGS="$HOST_CFLAGS -DXP_UNIX -DXP_MACOSX -DNO_X11"
     HOST_NSPR_MDCPUCFG='\"md/_darwin.cfg\"'
     HOST_OPTIMIZE_FLAGS="${HOST_OPTIMIZE_FLAGS=-O3}"
-    MOZ_FIX_LINK_PATHS='-Wl,-executable_path,$(LIBXUL_DIST)/bin'
-    LIBXUL_LIBS='$(XPCOM_FROZEN_LDOPTS) $(LIBXUL_DIST)/bin/XUL -lobjc'
+    LDFLAGS="$LDFLAGS -lobjc"
+    LIBXUL_LIBS='$(XPCOM_FROZEN_LDOPTS) $(LIBXUL_DIST)/bin/XUL'
     ;;
 
 *-linux*|*-kfreebsd*-gnu)
     HOST_CFLAGS="$HOST_CFLAGS -DXP_UNIX"
     HOST_NSPR_MDCPUCFG='\"md/_linux.cfg\"'
     HOST_OPTIMIZE_FLAGS="${HOST_OPTIMIZE_FLAGS=-O3}"
     ;;
 
@@ -1672,16 +1672,17 @@ case "$target" in
             AC_MSG_RESULT([yes])
             MOZ_OPTIMIZE_LDFLAGS="-Wl,-dead_strip"
         else
             AC_MSG_RESULT([no])
         fi
         
         LDFLAGS=$_SAVE_LDFLAGS
     fi
+    MOZ_FIX_LINK_PATHS='-Wl,-executable_path,$(LIBXUL_DIST)/bin'
     ;;
 
 *-freebsd*)
     if test `test -x /usr/bin/objformat && /usr/bin/objformat || echo elf` != "elf"; then
 	DLL_SUFFIX=".so.1.0"
 	DSO_LDOPTS="-shared"
     fi
     if test ! "$GNU_CC"; then
--- a/js/src/xpconnect/loader/XPCOMUtils.jsm
+++ b/js/src/xpconnect/loader/XPCOMUtils.jsm
@@ -277,16 +277,38 @@ var XPCOMUtils = {
    * Convenience access to category manager
    */
   get categoryManager() {
     return Components.classes["@mozilla.org/categorymanager;1"]
            .getService(Ci.nsICategoryManager);
   },
 
   /**
+   * Helper which iterates over a nsISimpleEnumerator.
+   * @param e The nsISimpleEnumerator to iterate over.
+   * @param i The expected interface for each element.
+   */
+  IterSimpleEnumerator: function XPCU_IterSimpleEnumerator(e, i)
+  {
+    while (e.hasMoreElements())
+      yield e.getNext().QueryInterface(i);
+  },
+
+  /**
+   * Helper which iterates over a string enumerator.
+   * @param e The string enumerator (nsIUTF8StringEnumerator or
+   *          nsIStringEnumerator) over which to iterate.
+   */
+  IterStringEnumerator: function XPCU_IterStringEnumerator(e)
+  {
+    while (e.hasMore())
+      yield e.getNext();
+  },
+
+  /**
    * Returns an nsIFactory for |component|.
    */
   _getFactory: function XPCOMUtils__getFactory(component) {
     var factory = component.prototype._xpcom_factory;
     if (!factory) {
       factory = {
         createInstance: function(outer, iid) {
           if (outer)
@@ -309,8 +331,9 @@ function makeQI(interfaceNames) {
     for each(let interfaceName in interfaceNames) {
       if (Ci[interfaceName].equals(iid))
         return this;
     }
 
     throw Cr.NS_ERROR_NO_INTERFACE;
   };
 }
+
--- a/js/src/xpconnect/src/xpcwrappednativescope.cpp
+++ b/js/src/xpconnect/src/xpcwrappednativescope.cpp
@@ -775,21 +775,17 @@ void DEBUG_CheckForComponentsInScope(JSC
         return;
 
     // This is pretty much always bad. It usually means that native code is
     // making a callback to an interface implemented in JavaScript, but the
     // document where the JS object was created has already been cleared and the
     // global properties of that document's window are *gone*. Generally this
     // indicates a problem that should be addressed in the design and use of the
     // callback code.
-#ifdef I_FOOLISHLY_WANT_TO_IGNORE_THIS_LIKE_THE_OTHER_CRAP_WE_PRINTF
-    NS_WARNING("XPConnect is being called on a scope without a 'Components' property!");
-#else
     NS_ERROR("XPConnect is being called on a scope without a 'Components' property!");
-#endif
 }
 #else
 #define DEBUG_CheckForComponentsInScope(ccx, obj, OKIfNotInitialized, runtime) \
     ((void)0)
 #endif
 
 // static
 XPCWrappedNativeScope*
--- a/js/src/xpconnect/tools/src/nsXPCToolsProfiler.cpp
+++ b/js/src/xpconnect/tools/src/nsXPCToolsProfiler.cpp
@@ -200,17 +200,17 @@ xpctools_InterpreterHook(JSContext *cx, 
     {
         nsXPCToolsProfiler* self = (nsXPCToolsProfiler*) closure;    
 
         PR_Lock(self->mLock);
 
         ProfilerFunction* fun;
         if (self->mScriptTable.Get(script, &fun))
         {
-            if(before == PR_TRUE)
+            if(before)
             {
                 fun->IncrementCallCount();
                 fun->SetStartTime();
             }
             else
             {
                 PRUint32 delta = fun->SetEndTime();
 
--- a/layout/base/nsCSSFrameConstructor.cpp
+++ b/layout/base/nsCSSFrameConstructor.cpp
@@ -17,17 +17,17 @@
  *
  * The Initial Developer of the Original Code is
  * Netscape Communications Corporation.
  * Portions created by the Initial Developer are Copyright (C) 1998
  * the Initial Developer. All Rights Reserved.
  *
  * Contributor(s):
  *   Dan Rosen <dr@netscape.com>
- *   Mats Palmgren <mats.palmgren@bredband.net>
+ *   Mats Palmgren <matspal@gmail.com>
  *
  * Alternatively, the contents of this file may be used under the terms of
  * either of the GNU General Public License Version 2 or later (the "GPL"),
  * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
  * in which case the provisions of the GPL or the LGPL are applicable instead
  * of those above. If you wish to allow use of your version of this file only
  * under the terms of either the GPL or the LGPL, and not to allow others to
  * use your version of this file under the terms of the MPL, indicate your
@@ -72,18 +72,16 @@
 #include "nsIDOMXULElement.h"
 #include "nsHTMLContainerFrame.h"
 #include "nsINameSpaceManager.h"
 #include "nsIDOMHTMLSelectElement.h"
 #include "nsIDOMHTMLLegendElement.h"
 #include "nsIComboboxControlFrame.h"
 #include "nsIListControlFrame.h"
 #include "nsISelectControlFrame.h"
-#include "nsIRadioControlFrame.h"
-#include "nsICheckboxControlFrame.h"
 #include "nsIDOMCharacterData.h"
 #include "nsIDOMHTMLImageElement.h"
 #include "nsPlaceholderFrame.h"
 #include "nsTableRowGroupFrame.h"
 #include "nsStyleChangeList.h"
 #include "nsIFormControl.h"
 #include "nsCSSAnonBoxes.h"
 #include "nsIDeviceContext.h"
@@ -251,16 +249,17 @@ static FrameCtorDebugFlags gFlags[] = {
 };
 
 #define NUM_DEBUG_FLAGS (sizeof(gFlags) / sizeof(gFlags[0]))
 #endif
 
 
 #ifdef MOZ_XUL
 #include "nsMenuFrame.h"
+#include "nsMenuPopupFrame.h"
 #include "nsPopupSetFrame.h"
 #include "nsTreeColFrame.h"
 #include "nsIBoxObject.h"
 #include "nsPIListBoxObject.h"
 #include "nsListBoxBodyFrame.h"
 #include "nsListItemFrame.h"
 #include "nsXULLabelFrame.h"
 
--- a/layout/base/nsPresContext.cpp
+++ b/layout/base/nsPresContext.cpp
@@ -839,17 +839,17 @@ nsPresContext::UpdateAfterPreferencesCha
   }
 
   RebuildAllStyleData(hint);
 }
 
 nsresult
 nsPresContext::Init(nsIDeviceContext* aDeviceContext)
 {
-  NS_ASSERTION(!(mInitialized == PR_TRUE), "attempt to reinit pres context");
+  NS_ASSERTION(!mInitialized, "attempt to reinit pres context");
   NS_ENSURE_ARG(aDeviceContext);
 
   mDeviceContext = aDeviceContext;
   NS_ADDREF(mDeviceContext);
 
   if (mDeviceContext->SetPixelScale(mFullZoom))
     mDeviceContext->FlushFontCache();
   mCurAppUnitsPerDevPixel = AppUnitsPerDevPixel();
@@ -1252,17 +1252,17 @@ nsPresContext::SetFullZoom(float aZoom)
   nscoord oldWidthAppUnits, oldHeightAppUnits;
   mShell->GetViewManager()->GetWindowDimensions(&oldWidthAppUnits, &oldHeightAppUnits);
   float oldWidthDevPixels = oldWidthAppUnits / float(mCurAppUnitsPerDevPixel);
   float oldHeightDevPixels = oldHeightAppUnits / float(mCurAppUnitsPerDevPixel);
   if (mDeviceContext->SetPixelScale(aZoom)) {
     mDeviceContext->FlushFontCache();
   }
 
-  NS_ASSERTION(mSupressResizeReflow == PR_FALSE, "two zooms happening at the same time? impossible!");
+  NS_ASSERTION(!mSupressResizeReflow, "two zooms happening at the same time? impossible!");
   mSupressResizeReflow = PR_TRUE;
 
   mFullZoom = aZoom;
   mShell->GetViewManager()->
     SetWindowDimensions(NSToCoordRound(oldWidthDevPixels * AppUnitsPerDevPixel()),
                         NSToCoordRound(oldHeightDevPixels * AppUnitsPerDevPixel()));
   if (HasCachedStyleData()) {
     MediaFeatureValuesChanged(PR_TRUE);
--- a/layout/base/nsPresShell.cpp
+++ b/layout/base/nsPresShell.cpp
@@ -20,17 +20,17 @@
  * Portions created by the Initial Developer are Copyright (C) 1998
  * the Initial Developer. All Rights Reserved.
  *
  * Contributor(s):
  *   Steve Clark <buster@netscape.com>
  *   Håkan Waara <hwaara@chello.se>
  *   Dan Rosen <dr@netscape.com>
  *   Daniel Glazman <glazman@netscape.com>
- *   Mats Palmgren <mats.palmgren@bredband.net>
+ *   Mats Palmgren <matspal@gmail.com>
  *
  * Alternatively, the contents of this file may be used under the terms of
  * either of the GNU General Public License Version 2 or later (the "GPL"),
  * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
  * in which case the provisions of the GPL or the LGPL are applicable instead
  * of those above. If you wish to allow use of your version of this file only
  * under the terms of either the GPL or the LGPL, and not to allow others to
  * use your version of this file under the terms of the MPL, indicate your
@@ -3018,62 +3018,29 @@ PresShell::CompleteScroll(PRBool aForwar
   return NS_OK;
 }
 
 NS_IMETHODIMP
 PresShell::CompleteMove(PRBool aForward, PRBool aExtend)
 {
   // Beware! This may flush notifications via synchronous
   // ScrollSelectionIntoView.
-
-  nsIContent* root = mSelection->GetAncestorLimiter();
-  nsIDocument* doc;
-  if (root && (doc = root->GetOwnerDoc()) && doc->GetRootContent() != root) {
-    // Make the caret be either at the very beginning (0) or the very end of
-    // root. Only do this when not moving to the beginning or end of the
-    // document (root is null or root is the documentElement), that's handled
-    // below by moving to beginning or end of the scrollable view.
-    nsIContent* node = root;
-    PRInt32 offset = 0;
-    nsFrameSelection::HINT hint = nsFrameSelection::HINTLEFT;
-    if (aForward) {
-      nsIContent* next = node;
-      PRUint32 count;
-      while ((count = next->GetChildCount()) > 0) {
-        node = next;
-        offset = count;
-        next = next->GetChildAt(count - 1);
-      }
-
-      if (offset > 0 && node->GetChildAt(offset - 1)->Tag() == nsGkAtoms::br) {
-        --offset;
-        hint = nsFrameSelection::HINTRIGHT; // for bug 106855
-      }
-    }
-
-    mSelection->HandleClick(node, offset, offset, aExtend, PR_FALSE, hint);
-
-    // HandleClick resets ancestorLimiter, so set it again.
-    mSelection->SetAncestorLimiter(root);
-
-    // After ScrollSelectionIntoView(), the pending notifications might be
-    // flushed and PresShell/PresContext/Frames may be dead. See bug 418470.
-    return
-      ScrollSelectionIntoView(nsISelectionController::SELECTION_NORMAL, 
-                              nsISelectionController::SELECTION_FOCUS_REGION,
-                              PR_TRUE);
-  }
-
-  nsIFrame *frame = FrameConstructor()->GetRootElementFrame();
+  nsIContent* limiter = mSelection->GetAncestorLimiter();
+  nsIFrame* frame = limiter ? limiter->GetPrimaryFrame()
+                            : FrameConstructor()->GetRootElementFrame();
   if (!frame)
     return NS_ERROR_FAILURE;
   nsPeekOffsetStruct pos = frame->GetExtremeCaretPosition(!aForward);
-
-  mSelection->HandleClick(pos.mResultContent ,pos.mContentOffset ,pos.mContentOffset/*End*/ ,aExtend, PR_FALSE, aForward);
-
+  mSelection->HandleClick(pos.mResultContent, pos.mContentOffset,
+                          pos.mContentOffset, aExtend, PR_FALSE, aForward);
+  if (limiter) {
+    // HandleClick resets ancestorLimiter, so set it again.
+    mSelection->SetAncestorLimiter(limiter);
+  }
+    
   // After ScrollSelectionIntoView(), the pending notifications might be
   // flushed and PresShell/PresContext/Frames may be dead. See bug 418470.
   return ScrollSelectionIntoView(nsISelectionController::SELECTION_NORMAL, 
                                  nsISelectionController::SELECTION_FOCUS_REGION,
                                  PR_TRUE);
 }
 
 NS_IMETHODIMP 
--- a/layout/base/tests/Makefile.in
+++ b/layout/base/tests/Makefile.in
@@ -86,16 +86,26 @@ DEFINES += -D_IMPL_NS_LAYOUT
 		test_bug458898.html \
 		test_bug465448.xul \
 		test_bug469170.html \
 		test_bug471126.html \
 		test_bug435293-scale.html \
 		test_bug435293-interaction.html \
 		test_bug435293-skew.html \
 		test_bug495648.xul \
+		test_reftests_with_caret.html \
+		     bug106855-1.html \
+		     bug106855-2.html \
+		     bug106855-1-ref.html \
+		     bug482484.html \
+		     bug482484-ref.html \
+		     bug512295-1.html \
+		     bug512295-1-ref.html \
+		     bug512295-2.html \
+		     bug512295-2-ref.html \
 		test_bug514127.html \
 		test_bug518777.html \
 		test_flush_on_paint.html \
 		test_scroll_selection_into_view.html \
 		test_scrolling.html \
 		$(NULL)
 # test_bug396024.html is currently disabled because it interacts badly with
 # the "You can't print-preview while the page is loading" dialog.
new file mode 100644
--- /dev/null
+++ b/layout/base/tests/bug106855-1-ref.html
@@ -0,0 +1,28 @@
+<!DOCTYPE HTML><html><head>
+  <script type="text/javascript" src="/MochiKit/packed.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/EventUtils.js"></script>
+</head>
+<body>
+x<br>
+<textarea id="t" rows="4">
+A
+
+
+</textarea><br>
+y
+<script>
+  // Position the caret at the last line
+  var sel = window.getSelection();
+  sel.removeAllRanges();
+
+  var area = document.getElementById('t');
+  area.focus();
+
+  sendKey('RIGHT', window);  // now after "A"
+  sendKey('RIGHT', window);  // 
+  sendKey('RIGHT', window);  // 
+  sendKey('RIGHT', window);  // now at the last line
+</script>
+
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/base/tests/bug106855-1.html
@@ -0,0 +1,26 @@
+<!DOCTYPE HTML><html><head>
+  <script type="text/javascript" src="/MochiKit/packed.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/EventUtils.js"></script>
+</head>
+<body>
+x<br>
+<textarea id="t" rows="4">
+A
+
+
+</textarea><br>
+y
+<script>
+  // Position the caret at the last line
+  var sel = window.getSelection();
+  sel.removeAllRanges();
+
+  var area = document.getElementById('t');
+  area.focus();
+
+  sendKey('DOWN', window);  // now after "A"
+  sendKey('DOWN', window);  // 
+  sendKey('DOWN', window);  // now at the last line
+</script>
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/base/tests/bug106855-2.html
@@ -0,0 +1,27 @@
+<!DOCTYPE HTML><html><head>
+  <script type="text/javascript" src="/MochiKit/packed.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/EventUtils.js"></script>
+</head>
+<body>
+x<br>
+<textarea id="t" rows="4">
+A
+
+
+</textarea><br>
+y
+<script>
+  // Position the caret at the last line
+  var sel = window.getSelection();
+  sel.removeAllRanges();
+
+  var area = document.getElementById('t');
+  area.focus();
+
+  sendKey('DOWN', window);  // now after "A"
+  sendKey('DOWN', window);  // 
+  sendKey('DOWN', window);  // 
+  sendKey('DOWN', window);  // now at the last line
+</script>
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/base/tests/bug482484-ref.html
@@ -0,0 +1,18 @@
+<!DOCTYPE HTML><html><head></head>
+<body>
+<div contentEditable="true" id="div"><p id="p">ABC</p></div>
+<script>
+  // Position the caret after the "A"
+  var div = document.getElementById('div');
+  var p = document.getElementById('p');
+  div.focus();
+  var sel = window.getSelection();
+  sel.removeAllRanges();
+  var range = document.createRange();
+  range.setStart(p.firstChild, 1)
+  range.setEnd(p.firstChild, 1);
+  sel.addRange(range);
+</script>
+
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/base/tests/bug482484.html
@@ -0,0 +1,23 @@
+<!DOCTYPE HTML><html><head>
+  <script type="text/javascript" src="/MochiKit/packed.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/EventUtils.js"></script>
+</head>
+<body>
+<div contentEditable="true" id="div"><p id="p">BC</p></div>
+<script>
+  // Position the caret before the "B"
+  var div = document.getElementById('div');
+  div.focus();
+  var p = document.getElementById('p');
+  var sel = window.getSelection();
+  sel.removeAllRanges();
+  var range = document.createRange();
+  range.setStart(p.firstChild, 0)
+  range.setEnd(p.firstChild, 0);
+  sel.addRange(range);
+
+  sendKey('UP', div);  // move UP
+  sendChar('A', div);  // insert "A"
+</script>
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/base/tests/bug512295-1-ref.html
@@ -0,0 +1,25 @@
+<!DOCTYPE HTML><html><head>
+  <script type="text/javascript" src="/MochiKit/packed.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/EventUtils.js"></script>
+</head>
+<body>
+<div contenteditable="true">
+<p id="p">A B CD EFG<br>
+  1234567890</p>
+</div>
+x
+<script>
+  // Position the caret at the end of the P element
+  var p = document.getElementById('p');
+  var div = p.parentNode;
+  div.focus();
+  var sel = window.getSelection();
+  sel.removeAllRanges();
+  var range = document.createRange();
+  range.setStart(p, p.childNodes.length);
+  range.setEnd(p, p.childNodes.length);
+  sel.addRange(range);
+</script>
+
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/base/tests/bug512295-1.html
@@ -0,0 +1,31 @@
+<!DOCTYPE HTML><html><head>
+  <script type="text/javascript" src="/MochiKit/packed.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/EventUtils.js"></script>
+</head>
+<body>
+<div contenteditable="true">
+<p id="p">A B CD EFG<br>
+  1234567890</p>
+</div>
+x
+<script>
+  // Position the caret after "A"
+  var sel = window.getSelection();
+  sel.removeAllRanges();
+  var range = document.createRange();
+  var p = document.getElementById('p');
+  var t = p.firstChild;
+  range.setStart(t, 1);
+  range.setEnd(t, 1);
+  sel.addRange(range);
+  p.parentNode.focus();
+
+  sendKey('DOWN', window);  // now after "1"
+  sendKey('DOWN', window);  // now make sure we get to the end
+  sendKey('DOWN', window);  // now make sure we get to the end
+  sendKey('DOWN', window);  // now make sure we get to the end
+  sendKey('DOWN', window);  // now make sure we get to the end
+  sendKey('DOWN', window);  // now make sure we get to the end
+</script>
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/base/tests/bug512295-2-ref.html
@@ -0,0 +1,25 @@
+<!DOCTYPE HTML><html><head>
+  <script type="text/javascript" src="/MochiKit/packed.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/EventUtils.js"></script>
+</head>
+<body>
+x
+<div contenteditable="true">
+<p id="p">A B CD EFG<br>
+  1234567890</p>
+</div>
+<script>
+  // Position the caret before the "A"
+  var p = document.getElementById('p');
+  var div = p.parentNode;
+  div.focus();
+  var sel = window.getSelection();
+  sel.removeAllRanges();
+  var range = document.createRange();
+  range.setStart(p.firstChild, 0);
+  range.setEnd(p.firstChild, 0);
+  sel.addRange(range);
+</script>
+
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/base/tests/bug512295-2.html
@@ -0,0 +1,31 @@
+<!DOCTYPE HTML><html><head>
+  <script type="text/javascript" src="/MochiKit/packed.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/EventUtils.js"></script>
+</head>
+<body>
+x
+<div contenteditable="true">
+<p id="p">A B CD EFG<br>
+  1234567890</p>
+</div>
+<script>
+  // Position the caret after "A"
+  var sel = window.getSelection();
+  sel.removeAllRanges();
+  var range = document.createRange();
+  var p = document.getElementById('p');
+  var t = p.firstChild;
+  range.setStart(t, 1);
+  range.setEnd(t, 1);
+  sel.addRange(range);
+  p.parentNode.focus();
+
+  sendKey('DOWN', window);  // now after "1"
+  sendKey('DOWN', window);  // now below the P element
+  sendKey('UP', window);    // now before the "1"
+  sendKey('UP', window);    // now before the "A"
+  sendKey('UP', window);    // now before the "A"
+  sendKey('UP', window);    // now before the "A"
+</script>
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/base/tests/test_reftests_with_caret.html
@@ -0,0 +1,112 @@
+<!DOCTYPE HTML>
+<html>
+<head>
+  <title>Reftests with caret drawing</title>
+  <script type="text/javascript" src="/MochiKit/packed.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/EventUtils.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/WindowSnapshot.js"></script>
+  <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
+<script type="text/javascript">
+
+var canvases = [];
+function callbackTestCanvas(canvas)
+{
+  canvases.push(canvas);
+
+  if (canvases.length != 2)
+    return;
+
+  var result = canvases[0];
+  var reference = canvases[1];
+
+  var ret = compareSnapshots(result.snapshot, reference.snapshot, true);
+  ok(ret[0], "Reftest " + result.src +
+             (ret[0] ? "" : (" FAILED\n" +
+              "RESULT=" + ret[1] + "\n" +
+              "REFERENCE=" + ret[2] + "\n")));
+
+  // Remove the iframes if the test was successful
+  if (ret[0]) {
+    result.parentNode.removeChild(result);
+    reference.parentNode.removeChild(reference);
+  }
+  canvases = [];
+  nextTest();
+}
+
+function doSnapShot(iframe) {
+  iframe.snapshot = snapshotWindow(iframe.contentWindow, true);
+  callbackTestCanvas(iframe);
+};
+
+function remotePageLoaded() {
+  var iframe = this;
+  setTimeout(function(){doSnapShot(iframe);}, 0)
+};
+
+function createIframe(url,next) {
+  var iframe = document.createElement("iframe");
+  iframe.src = url;
+  iframe.remotePageLoaded = remotePageLoaded;
+  var me = this;
+  iframe.addEventListener("load", function() {
+      iframe.remotePageLoaded();
+      if (next) setTimeout(function(){createIframe(next,null);}, 0)
+    }, false);
+  window.document.body.appendChild(iframe);
+};
+
+function refTest(test,ref) {
+  createIframe(test,ref);
+};
+
+var caretBlinkTime;
+function endTest() {
+  SimpleTest.finish();
+  netscape.security.PrivilegeManager.enablePrivilege(
+   'UniversalPreferencesRead UniversalPreferencesWrite UniversalXPConnect');
+  var prefs = Components.classes["@mozilla.org/preferences-service;1"]
+                        .getService(Components.interfaces.nsIPrefBranch);
+  prefs.setIntPref("ui.caretBlinkTime", caretBlinkTime);
+}
+
+var tests = [
+    [ 'bug106855-1.html' , 'bug106855-1-ref.html' ] ,
+    [ 'bug106855-2.html' , 'bug106855-1-ref.html' ] ,
+    [ 'bug482484.html'   , 'bug482484-ref.html'   ] ,
+    [ 'bug512295-1.html' , 'bug512295-1-ref.html' ] ,
+    [ 'bug512295-2.html' , 'bug512295-2-ref.html' ]
+];
+var testIndex = 0;
+
+function nextTest() {
+  if (testIndex < tests.length) {
+    refTest(tests[testIndex][0],tests[testIndex][1]);
+    ++testIndex;
+  } else {
+    endTest();
+  }
+}
+function runTests() {
+  try {
+    SimpleTest.waitForExplicitFinish();
+
+    netscape.security.PrivilegeManager.enablePrivilege(
+      'UniversalPreferencesRead UniversalPreferencesWrite UniversalXPConnect');
+    var prefs = Components.classes["@mozilla.org/preferences-service;1"]
+                          .getService(Components.interfaces.nsIPrefBranch);
+    caretBlinkTime = prefs.getIntPref("ui.caretBlinkTime");
+    prefs.setIntPref("ui.caretBlinkTime", -1);
+
+    nextTest();
+  } catch(e) {
+    endTest();
+  }
+}
+
+</script>
+</head>
+<body onload="runTests()">
+</body>
+</html>
--- a/layout/forms/Makefile.in
+++ b/layout/forms/Makefile.in
@@ -53,18 +53,16 @@ LIBRARY_NAME	= gkforms_s
 LIBXUL_LIBRARY	= 1
 
 
 
 EXPORTS		= \
 		nsIListControlFrame.h \
 		nsIComboboxControlFrame.h \
 		nsIFormControlFrame.h \
-		nsIRadioControlFrame.h \
-		nsICheckboxControlFrame.h \
 		nsISelectControlFrame.h \
 		nsITextControlFrame.h \
 		$(NULL)
 
 CPPSRCS		= \
 		nsButtonFrameRenderer.cpp \
 		nsComboboxControlFrame.cpp \
 		nsFieldSetFrame.cpp \
--- a/layout/forms/nsFileControlFrame.cpp
+++ b/layout/forms/nsFileControlFrame.cpp
@@ -442,17 +442,17 @@ nsFileControlFrame::FetchLastUsedDirecto
     return NS_ERROR_OUT_OF_MEMORY;
   uri->SetAsISupports(aURI);
   NS_NAMED_LITERAL_STRING(prefName, "lastUploadDirectory");
 
   // Get the last used directory, if it is stored
   PRBool hasPref;
   if (NS_SUCCEEDED(contentPrefService->HasPref(uri, prefName, &hasPref)) && hasPref) {
     nsCOMPtr<nsIVariant> pref;
-    contentPrefService->GetPref(uri, prefName, getter_AddRefs(pref));
+    contentPrefService->GetPref(uri, prefName, nsnull, getter_AddRefs(pref));
     nsString prefStr;
     pref->GetAsAString(prefStr);
     return aFile->InitWithPath(prefStr);
   }
   return NS_OK;
 }
 
 void
--- a/layout/forms/nsGfxCheckboxControlFrame.cpp
+++ b/layout/forms/nsGfxCheckboxControlFrame.cpp
@@ -114,21 +114,16 @@ nsGfxCheckboxControlFrame::nsGfxCheckbox
 : nsFormControlFrame(aContext)
 {
 }
 
 nsGfxCheckboxControlFrame::~nsGfxCheckboxControlFrame()
 {
 }
 
-
-NS_QUERYFRAME_HEAD(nsGfxCheckboxControlFrame)
-  NS_QUERYFRAME_ENTRY(nsICheckboxControlFrame)
-NS_QUERYFRAME_TAIL_INHERITING(nsFormControlFrame)
-
 #ifdef ACCESSIBILITY
 NS_IMETHODIMP
 nsGfxCheckboxControlFrame::GetAccessible(nsIAccessible** aAccessible)
 {
   nsCOMPtr<nsIAccessibilityService> accService
     = do_GetService("@mozilla.org/accessibilityService;1");
 
   if (accService) {
@@ -137,25 +132,16 @@ nsGfxCheckboxControlFrame::GetAccessible
   }
 
   return NS_ERROR_FAILURE;
 }
 #endif
 
 //------------------------------------------------------------
 NS_IMETHODIMP
-nsGfxCheckboxControlFrame::OnChecked(nsPresContext* aPresContext,
-                                     PRBool aChecked)
-{
-  InvalidateOverflowRect();
-  return NS_OK;
-}
-
-//------------------------------------------------------------
-NS_IMETHODIMP
 nsGfxCheckboxControlFrame::BuildDisplayList(nsDisplayListBuilder*   aBuilder,
                                             const nsRect&           aDirtyRect,
                                             const nsDisplayListSet& aLists)
 {
   nsresult rv = nsFormControlFrame::BuildDisplayList(aBuilder, aDirtyRect,
                                                      aLists);
   NS_ENSURE_SUCCESS(rv, rv);
   
--- a/layout/forms/nsGfxCheckboxControlFrame.h
+++ b/layout/forms/nsGfxCheckboxControlFrame.h
@@ -33,24 +33,22 @@
  * the provisions above, a recipient may use your version of this file under
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 #ifndef nsGfxCheckboxControlFrame_h___
 #define nsGfxCheckboxControlFrame_h___
 
 #include "nsFormControlFrame.h"
-#include "nsICheckboxControlFrame.h"
 
 #ifdef ACCESSIBILITY
 class nsIAccessible;
 #endif
 
-class nsGfxCheckboxControlFrame : public nsFormControlFrame,
-                                  public nsICheckboxControlFrame
+class nsGfxCheckboxControlFrame : public nsFormControlFrame
 {
 public:
   NS_DECL_FRAMEARENA_HELPERS
 
   nsGfxCheckboxControlFrame(nsStyleContext* aContext);
   virtual ~nsGfxCheckboxControlFrame();
 
 #ifdef DEBUG
@@ -62,21 +60,16 @@ public:
   NS_IMETHOD BuildDisplayList(nsDisplayListBuilder*   aBuilder,
                               const nsRect&           aDirtyRect,
                               const nsDisplayListSet& aLists);
 
 #ifdef ACCESSIBILITY
   NS_IMETHOD GetAccessible(nsIAccessible** aAccessible);
 #endif
 
-  //nsICheckboxControlFrame methods
-  NS_IMETHOD OnChecked(nsPresContext* aPresContext, PRBool aChecked);
-
-  NS_DECL_QUERYFRAME
-
 protected:
 
   PRBool IsChecked();
   PRBool IsIndeterminate();
 };
 
 #endif
 
--- a/layout/forms/nsGfxRadioControlFrame.cpp
+++ b/layout/forms/nsGfxRadioControlFrame.cpp
@@ -59,20 +59,16 @@ nsGfxRadioControlFrame::nsGfxRadioContro
   nsFormControlFrame(aContext)
 {
 }
 
 nsGfxRadioControlFrame::~nsGfxRadioControlFrame()
 {
 }
 
-NS_QUERYFRAME_HEAD(nsGfxRadioControlFrame)
-  NS_QUERYFRAME_ENTRY(nsIRadioControlFrame)
-NS_QUERYFRAME_TAIL_INHERITING(nsFormControlFrame)
-
 #ifdef ACCESSIBILITY
 NS_IMETHODIMP
 nsGfxRadioControlFrame::GetAccessible(nsIAccessible** aAccessible)
 {
   nsCOMPtr<nsIAccessibilityService> accService
     = do_GetService("@mozilla.org/accessibilityService;1");
 
   if (accService) {
@@ -121,16 +117,8 @@ nsGfxRadioControlFrame::BuildDisplayList
   PRBool checked = PR_TRUE;
   GetCurrentCheckState(&checked); // Get check state from the content model
   if (!checked)
     return NS_OK;
     
   return aLists.Content()->AppendNewToTop(new (aBuilder)
     nsDisplayGeneric(this, PaintCheckedRadioButton, "CheckedRadioButton"));
 }
-
-NS_IMETHODIMP
-nsGfxRadioControlFrame::OnChecked(nsPresContext* aPresContext,
-                                  PRBool aChecked)
-{
-  InvalidateOverflowRect();
-  return NS_OK;
-}
--- a/layout/forms/nsGfxRadioControlFrame.h
+++ b/layout/forms/nsGfxRadioControlFrame.h
@@ -34,38 +34,33 @@
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 
 #ifndef nsGfxRadioControlFrame_h___
 #define nsGfxRadioControlFrame_h___
 
 #include "nsFormControlFrame.h"
-#include "nsIRadioControlFrame.h"
 
 #ifdef ACCESSIBILITY
 class nsIAccessible;
 #endif
 
 // nsGfxRadioControlFrame
 
-class nsGfxRadioControlFrame : public nsFormControlFrame,
-                               public nsIRadioControlFrame
-
+class nsGfxRadioControlFrame : public nsFormControlFrame
 {
 public:
   nsGfxRadioControlFrame(nsStyleContext* aContext);
   ~nsGfxRadioControlFrame();
 
-  NS_DECL_QUERYFRAME
   NS_DECL_FRAMEARENA_HELPERS
 
 #ifdef ACCESSIBILITY
   NS_IMETHOD GetAccessible(nsIAccessible** aAccessible);
 #endif
-  NS_IMETHOD OnChecked(nsPresContext* aPresContext, PRBool aChecked);
 
   NS_IMETHOD BuildDisplayList(nsDisplayListBuilder*   aBuilder,
                               const nsRect&           aDirtyRect,
                               const nsDisplayListSet& aLists);
 };
 
 #endif
deleted file mode 100644
--- a/layout/forms/nsICheckboxControlFrame.h
+++ /dev/null
@@ -1,61 +0,0 @@
-/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* ***** BEGIN LICENSE BLOCK *****
- * Version: MPL 1.1/GPL 2.0/LGPL 2.1
- *
- * The contents of this file are subject to the Mozilla Public License Version
- * 1.1 (the "License"); you may not use this file except in compliance with
- * the License. You may obtain a copy of the License at
- * http://www.mozilla.org/MPL/
- *
- * Software distributed under the License is distributed on an "AS IS" basis,
- * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
- * for the specific language governing rights and limitations under the
- * License.
- *
- * The Original Code is mozilla.org code.
- *
- * The Initial Developer of the Original Code is
- * Netscape Communications Corporation.
- * Portions created by the Initial Developer are Copyright (C) 1998
- * the Initial Developer. All Rights Reserved.
- *
- * Contributor(s):
- *
- * Alternatively, the contents of this file may be used under the terms of
- * either of the GNU General Public License Version 2 or later (the "GPL"),
- * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
- * in which case the provisions of the GPL or the LGPL are applicable instead
- * of those above. If you wish to allow use of your version of this file only
- * under the terms of either the GPL or the LGPL, and not to allow others to
- * use your version of this file under the terms of the MPL, indicate your
- * decision by deleting the provisions above and replace them with the notice
- * and other provisions required by the GPL or the LGPL. If you do not delete
- * the provisions above, a recipient may use your version of this file under
- * the terms of any one of the MPL, the GPL or the LGPL.
- *
- * ***** END LICENSE BLOCK ***** */
-
-#ifndef nsICheckControlFrame_h___
-#define nsICheckControlFrame_h___
-
-#include "nsQueryFrame.h"
-class nsStyleContext;
-class nsPresContext;
-
-/** 
-  * nsICheckControlFrame is the common interface radio buttons.
-  * @see nsFromControlFrame and its base classes for more info
-  */
-class nsICheckboxControlFrame
-{
-public:
-  NS_DECL_QUERYFRAME_TARGET(nsICheckboxControlFrame)
-  
-  /**
-   * Called by content when checkbox "checked" changes
-   */
-  NS_IMETHOD OnChecked(nsPresContext* aPresContext, PRBool aChecked) = 0;
-};
-
-#endif
-
deleted file mode 100644
--- a/layout/forms/nsIRadioControlFrame.h
+++ /dev/null
@@ -1,60 +0,0 @@
-/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* ***** BEGIN LICENSE BLOCK *****
- * Version: MPL 1.1/GPL 2.0/LGPL 2.1
- *
- * The contents of this file are subject to the Mozilla Public License Version
- * 1.1 (the "License"); you may not use this file except in compliance with
- * the License. You may obtain a copy of the License at
- * http://www.mozilla.org/MPL/
- *
- * Software distributed under the License is distributed on an "AS IS" basis,
- * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
- * for the specific language governing rights and limitations under the
- * License.
- *
- * The Original Code is mozilla.org code.
- *
- * The Initial Developer of the Original Code is
- * Netscape Communications Corporation.
- * Portions created by the Initial Developer are Copyright (C) 1998
- * the Initial Developer. All Rights Reserved.
- *
- * Contributor(s):
- *
- * Alternatively, the contents of this file may be used under the terms of
- * either of the GNU General Public License Version 2 or later (the "GPL"),
- * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
- * in which case the provisions of the GPL or the LGPL are applicable instead
- * of those above. If you wish to allow use of your version of this file only
- * under the terms of either the GPL or the LGPL, and not to allow others to
- * use your version of this file under the terms of the MPL, indicate your
- * decision by deleting the provisions above and replace them with the notice
- * and other provisions required by the GPL or the LGPL. If you do not delete
- * the provisions above, a recipient may use your version of this file under
- * the terms of any one of the MPL, the GPL or the LGPL.
- *
- * ***** END LICENSE BLOCK ***** */
-
-#ifndef nsIRadioControlFrame_h___
-#define nsIRadioControlFrame_h___
-
-#include "nsQueryFrame.h"
-class nsStyleContext;
-
-/** 
-  * nsIRadioControlFrame is the common interface radio buttons.
-  * @see nsFormControlFrame and its base classes for more info
-  */
-class nsIRadioControlFrame
-{
-public:
-  NS_DECL_QUERYFRAME_TARGET(nsIRadioControlFrame)
-
-   /**
-    * Called by content when the radio button's state changes
-    */
-   NS_IMETHOD OnChecked(nsPresContext* aPresContext, PRBool aChecked) = 0;
-};
-
-#endif
-
--- a/layout/forms/nsListControlFrame.cpp
+++ b/layout/forms/nsListControlFrame.cpp
@@ -1448,17 +1448,17 @@ PRBool nsListControlFrame::CheckIfAllFra
 NS_IMETHODIMP
 nsListControlFrame::DoneAddingChildren(PRBool aIsDone)
 {
   mIsAllContentHere = aIsDone;
   if (mIsAllContentHere) {
     // Here we check to see if all the frames have been created 
     // for all the content.
     // If so, then we can initialize;
-    if (mIsAllFramesHere == PR_FALSE) {
+    if (!mIsAllFramesHere) {
       // if all the frames are now present we can initialize
       if (CheckIfAllFramesHere()) {
         mHasBeenInitialized = PR_TRUE;
         ResetList(PR_TRUE);
       }
     }
   }
   return NS_OK;
--- a/layout/forms/nsTextControlFrame.cpp
+++ b/layout/forms/nsTextControlFrame.cpp
@@ -1094,16 +1094,19 @@ void
 nsTextControlFrame::DestroyFrom(nsIFrame* aDestructRoot)
 {
   if (mInSecureKeyboardInputMode) {
     MaybeEndSecureKeyboardInput();
   }
   if (!mDidPreDestroy) {
     PreDestroy();
   }
+  if (mAnonymousDiv && mMutationObserver) {
+    mAnonymousDiv->RemoveMutationObserver(mMutationObserver);
+  }
   nsContentUtils::DestroyAnonymousContent(&mAnonymousDiv);
   nsBoxFrame::DestroyFrom(aDestructRoot);
 }
 
 nsIAtom*
 nsTextControlFrame::GetType() const 
 { 
   return nsGkAtoms::textInputFrame;
@@ -1600,16 +1603,20 @@ nsTextControlFrame::CreateAnonymousConte
     // crash when the number of lines exceeds the height of the textarea and
     // setting -moz-hidden-unscrollable overflow (NS_STYLE_OVERFLOW_CLIP)
     // doesn't paint the caret for some reason.
     const nsStyleDisplay* disp = GetStyleDisplay();
     if (disp->mOverflowX != NS_STYLE_OVERFLOW_VISIBLE &&
         disp->mOverflowX != NS_STYLE_OVERFLOW_CLIP) {
       classValue.AppendLiteral(" inherit-overflow");
     }
+
+    mMutationObserver = new nsAnonDivObserver(this);
+    NS_ENSURE_TRUE(mMutationObserver, NS_ERROR_OUT_OF_MEMORY);
+    mAnonymousDiv->AddMutationObserver(mMutationObserver);
   }
   rv = mAnonymousDiv->SetAttr(kNameSpaceID_None, nsGkAtoms::_class,
                               classValue, PR_FALSE);
   NS_ENSURE_SUCCESS(rv, rv);
 
   if (!aElements.AppendElement(mAnonymousDiv))
     return NS_ERROR_OUT_OF_MEMORY;
 
@@ -1877,17 +1884,17 @@ nsresult nsTextControlFrame::SetFormProp
       // Select all the text.
       //
       // XXX: This is lame, we can't call mEditor->SelectAll()
       //      because that triggers AutoCopies in unix builds.
       //      Instead, we have to call our own homegrown version
       //      of select all which merely builds a range that selects
       //      all of the content and adds that to the selection.
 
-      SelectAllContents();
+      SelectAllOrCollapseToEndOfText(PR_TRUE);
     }
     mIsProcessing = PR_FALSE;
   }
   return NS_OK;
 }      
 
 nsresult
 nsTextControlFrame::GetFormProperty(nsIAtom* aName, nsAString& aValue) const
@@ -1959,41 +1966,49 @@ nsTextControlFrame::SetSelectionInternal
   rv = selection->RemoveAllRanges();  
 
   NS_ENSURE_SUCCESS(rv, rv);
 
   return selection->AddRange(range);
 }
 
 nsresult
-nsTextControlFrame::SelectAllContents()
+nsTextControlFrame::SelectAllOrCollapseToEndOfText(PRBool aSelect)
 {
   if (!mEditor)
     return NS_OK;
 
   nsCOMPtr<nsIDOMElement> rootElement;
   nsresult rv = mEditor->GetRootElement(getter_AddRefs(rootElement));
   NS_ENSURE_SUCCESS(rv, rv);
 
   nsCOMPtr<nsIContent> rootContent = do_QueryInterface(rootElement);
+  nsCOMPtr<nsIDOMNode> rootNode(do_QueryInterface(rootElement));
   PRInt32 numChildren = rootContent->GetChildCount();
 
   if (numChildren > 0) {
     // We never want to place the selection after the last
     // br under the root node!
     nsIContent *child = rootContent->GetChildAt(numChildren - 1);
     if (child) {
       if (child->Tag() == nsGkAtoms::br)
         --numChildren;
     }
+    if (!aSelect && numChildren) {
+      child = rootContent->GetChildAt(numChildren - 1);
+      if (child && child->IsNodeOfType(nsINode::eTEXT)) {
+        rootNode = do_QueryInterface(child);
+        const nsTextFragment* fragment = child->GetText();
+        numChildren = fragment ? fragment->GetLength() : 0;
+      }
+    }
   }
 
-  nsCOMPtr<nsIDOMNode> rootNode(do_QueryInterface(rootElement));
-
-  return SetSelectionInternal(rootNode, 0, rootNode, numChildren);
+  return SetSelectionInternal(rootNode, aSelect ? 0 : numChildren,
+                              rootNode, numChildren);
 }
 
 nsresult
 nsTextControlFrame::SetSelectionEndPoints(PRInt32 aSelStart, PRInt32 aSelEnd)
 {
   NS_ASSERTION(aSelStart <= aSelEnd, "Invalid selection offsets!");
 
   if (aSelStart > aSelEnd)
@@ -2389,28 +2404,28 @@ nsTextControlFrame::AttributeChanged(PRI
   else {
     rv = nsBoxFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType);
   }
 
   return rv;
 }
 
 
-NS_IMETHODIMP
-nsTextControlFrame::GetText(nsString* aText)
+nsresult
+nsTextControlFrame::GetText(nsString& aText)
 {
   nsresult rv = NS_OK;
   if (IsSingleLineTextControl()) {
     // If we're going to remove newlines anyway, ignore the wrap property
-    GetValue(*aText, PR_TRUE);
-    RemoveNewlines(*aText);
+    GetValue(aText, PR_TRUE);
+    RemoveNewlines(aText);
   } else {
     nsCOMPtr<nsIDOMHTMLTextAreaElement> textArea = do_QueryInterface(mContent);
     if (textArea) {
-      rv = textArea->GetValue(*aText);
+      rv = textArea->GetValue(aText);
     }
   }
   return rv;
 }
 
 
 nsresult
 nsTextControlFrame::GetPhonetic(nsAString& aPhonetic)
@@ -2470,24 +2485,24 @@ nsTextControlFrame::FireOnInput()
   // DOM rules.
   nsCOMPtr<nsIPresShell> shell = PresContext()->PresShell();
   shell->HandleEventWithTarget(&event, nsnull, mContent, &status);
 }
 
 nsresult
 nsTextControlFrame::InitFocusedValue()
 {
-  return GetText(&mFocusedValue);
+  return GetText(mFocusedValue);
 }
 
 NS_IMETHODIMP
 nsTextControlFrame::CheckFireOnChange()
 {
   nsString value;
-  GetText(&value);
+  GetText(value);
   if (!mFocusedValue.Equals(value))
   {
     mFocusedValue = value;
     // Dispatch the change event
     nsEventStatus status = nsEventStatus_eIgnore;
     nsInputEvent event(PR_TRUE, NS_FORM_CHANGE, nsnull);
     nsCOMPtr<nsIPresShell> shell = PresContext()->PresShell();
     shell->HandleEventWithTarget(&event, nsnull, mContent, &status);
@@ -2501,16 +2516,22 @@ nsTextControlFrame::CheckFireOnChange()
 NS_IMETHODIMP
 nsTextControlFrame::GetValue(nsAString& aValue, PRBool aIgnoreWrap) const
 {
   aValue.Truncate();  // initialize out param
   nsresult rv = NS_OK;
   
   if (mEditor && mUseEditor) 
   {
+    PRBool canCache = aIgnoreWrap && !IsSingleLineTextControl();
+    if (canCache && !mCachedValue.IsEmpty()) {
+      aValue = mCachedValue;
+      return NS_OK;
+    }
+
     PRUint32 flags = (nsIDocumentEncoder::OutputLFLineBreak |
                       nsIDocumentEncoder::OutputPreformatted |
                       nsIDocumentEncoder::OutputPersistNBSP);
 
     if (PR_TRUE==IsPlainTextControl())
     {
       flags |= nsIDocumentEncoder::OutputBodyOnly;
     }
@@ -2537,16 +2558,21 @@ nsTextControlFrame::GetValue(nsAString& 
     // this.
     { /* Scope for context pusher */
       nsCxPusher pusher;
       pusher.PushNull();
       
       rv = mEditor->OutputToString(NS_LITERAL_STRING("text/plain"), flags,
                                    aValue);
     }
+    if (canCache) {
+      const_cast<nsTextControlFrame*>(this)->mCachedValue = aValue;
+    } else {
+      const_cast<nsTextControlFrame*>(this)->mCachedValue.Truncate();
+    }
   }
   else
   {
     // Otherwise get the value from content.
     nsCOMPtr<nsIDOMHTMLInputElement> inputControl = do_QueryInterface(mContent);
     if (inputControl)
     {
       rv = inputControl->GetValue(aValue);
@@ -2575,42 +2601,40 @@ nsTextControlFrame::SetValue(const nsASt
   // so much easier...
   if (mEditor && mUseEditor) 
   {
     // This method isn't used for user-generated changes, except for calls
     // from nsFileControlFrame which sets mFireChangeEventState==true and
     // restores it afterwards (ie. we want 'change' events for those changes).
     // Focused value must be updated to prevent incorrect 'change' events,
     // but only if user hasn't changed the value.
-    nsString val;
-    GetText(&val);
+
+    // GetText removes newlines from single line control.
+    nsString currentValue;
+    GetText(currentValue);
     PRBool focusValueInit = !mFireChangeEventState &&
-      mFocusedValue.Equals(val);
+      mFocusedValue.Equals(currentValue);
 
     nsCOMPtr<nsIEditor> editor = mEditor;
     nsWeakFrame weakFrame(this);
-    nsAutoString currentValue;
-    GetValue(currentValue, PR_FALSE);
-    if (IsSingleLineTextControl())
-    {
-      RemoveNewlines(currentValue); 
-    }
+
     // this is necessary to avoid infinite recursion
     if (!currentValue.Equals(aValue))
     {
       // \r is an illegal character in the dom, but people use them,
       // so convert windows and mac platform linebreaks to \n:
       // Unfortunately aValue is declared const, so we have to copy
       // in order to do this substitution.
-      currentValue.Assign(aValue);
-      ::PlatformToDOMLineBreaks(currentValue);
-
-      nsCOMPtr<nsIDOMDocument>domDoc;
-      nsresult rv = editor->GetDocument(getter_AddRefs(domDoc));
-      NS_ENSURE_SUCCESS(rv, rv);
+      nsString newValue(aValue);
+      if (aValue.FindChar(PRUnichar('\r')) != -1) {
+        ::PlatformToDOMLineBreaks(newValue);
+      }
+
+      nsCOMPtr<nsIDOMDocument> domDoc;
+      editor->GetDocument(getter_AddRefs(domDoc));
       NS_ENSURE_STATE(domDoc);
 
       PRBool outerTransaction;
       // Time to mess with our security context... See comments in GetValue()
       // for why this is needed.  Note that we have to do this up here, because
       // otherwise SelectAll() will fail.
       { /* Scope for context pusher */
         nsCxPusher pusher;
@@ -2623,17 +2647,29 @@ nsTextControlFrame::SetValue(const nsASt
         if (domSel)
         {
           selPriv = do_QueryInterface(domSel);
           if (selPriv)
             selPriv->StartBatchChanges();
         }
 
         nsCOMPtr<nsISelectionController> kungFuDeathGrip = mSelCon.get();
-        mSelCon->SelectAll();
+        PRUint32 currentLength = currentValue.Length();
+        PRUint32 newlength = newValue.Length();
+        if (!currentLength ||
+            !StringBeginsWith(newValue, currentValue)) {
+          // Replace the whole text.
+          currentLength = 0;
+          mSelCon->SelectAll();
+        } else {
+          // Collapse selection to the end so that we can append data.
+          SelectAllOrCollapseToEndOfText(PR_FALSE);
+        }
+        const nsAString& insertValue =
+          StringTail(newValue, newlength - currentLength);
         nsCOMPtr<nsIPlaintextEditor> plaintextEditor = do_QueryInterface(editor);
         if (!plaintextEditor || !weakFrame.IsAlive()) {
           NS_WARNING("Somehow not a plaintext editor?");
           return NS_ERROR_FAILURE;
         }
 
         // Since this code does not handle user-generated changes to the text,
         // make sure we don't fire oninput when the editor notifies us.
@@ -2657,21 +2693,24 @@ nsTextControlFrame::SetValue(const nsASt
         flags |= nsIPlaintextEditor::eEditorDontEchoPassword;
         editor->SetFlags(flags);
 
         // Also don't enforce max-length here
         PRInt32 savedMaxLength;
         plaintextEditor->GetMaxTextLength(&savedMaxLength);
         plaintextEditor->SetMaxTextLength(-1);
 
-        if (currentValue.Length() < 1)
+        if (insertValue.IsEmpty()) {
           editor->DeleteSelection(nsIEditor::eNone);
-        else {
-          if (plaintextEditor)
-            plaintextEditor->InsertText(currentValue);
+        } else {
+          plaintextEditor->InsertText(insertValue);
+        }
+
+        if (!IsSingleLineTextControl()) {
+          mCachedValue = newValue;
         }
 
         plaintextEditor->SetMaxTextLength(savedMaxLength);
         editor->SetFlags(savedFlags);
         if (selPriv)
           selPriv->EndBatchChanges();
       }
 
@@ -2757,8 +2796,45 @@ nsTextControlFrame::SetValueChanged(PRBo
 }
 
 /* static */ void
 nsTextControlFrame::ShutDown()
 {
   NS_IF_RELEASE(sNativeTextAreaBindings);
   NS_IF_RELEASE(sNativeInputBindings);
 }
+
+NS_IMPL_ISUPPORTS1(nsAnonDivObserver, nsIMutationObserver)
+
+void
+nsAnonDivObserver::CharacterDataChanged(nsIDocument*             aDocument,
+                                        nsIContent*              aContent,
+                                        CharacterDataChangeInfo* aInfo)
+{
+  mTextControl->ClearValueCache();
+}
+
+void
+nsAnonDivObserver::ContentAppended(nsIDocument* aDocument,
+                                   nsIContent*  aContainer,
+                                   PRInt32      aNewIndexInContainer)
+{
+  mTextControl->ClearValueCache();
+}
+
+void
+nsAnonDivObserver::ContentInserted(nsIDocument* aDocument,
+                                   nsIContent*  aContainer,
+                                   nsIContent*  aChild,
+                                   PRInt32      aIndexInContainer)
+{
+  mTextControl->ClearValueCache();
+}
+
+void
+nsAnonDivObserver::ContentRemoved(nsIDocument* aDocument,
+                                  nsIContent*  aContainer,
+                                  nsIContent*  aChild,
+                                  PRInt32      aIndexInContainer)
+{
+  mTextControl->ClearValueCache();
+}
+
--- a/layout/forms/nsTextControlFrame.h
+++ b/layout/forms/nsTextControlFrame.h
@@ -45,26 +45,43 @@
 #include "nsIAnonymousContentCreator.h"
 #include "nsIEditor.h"
 #include "nsITextControlFrame.h"
 #include "nsIFontMetrics.h"
 #include "nsWeakReference.h" //for service and presshell pointers
 #include "nsContentUtils.h"
 #include "nsDisplayList.h"
 #include "nsIScrollableFrame.h"
+#include "nsStubMutationObserver.h"
 
 class nsIEditor;
 class nsISelectionController;
 class nsTextInputSelectionImpl;
 class nsTextInputListener;
 class nsIDOMCharacterData;
 #ifdef ACCESSIBILITY
 class nsIAccessible;
 #endif
 class nsTextInputSelectionImpl;
+class nsTextControlFrame;
+
+class nsAnonDivObserver : public nsStubMutationObserver
+{
+public:
+  nsAnonDivObserver(nsTextControlFrame* aTextControl)
+  : mTextControl(aTextControl) {}
+  NS_DECL_ISUPPORTS
+  NS_DECL_NSIMUTATIONOBSERVER_CHARACTERDATACHANGED
+  NS_DECL_NSIMUTATIONOBSERVER_CONTENTAPPENDED
+  NS_DECL_NSIMUTATIONOBSERVER_CONTENTINSERTED
+  NS_DECL_NSIMUTATIONOBSERVER_CONTENTREMOVED
+
+private:
+  nsTextControlFrame* mTextControl;
+};
 
 class nsTextControlFrame : public nsStackFrame,
                            public nsIAnonymousContentCreator,
                            public nsITextControlFrame
 {
 public:
   NS_DECL_FRAMEARENA_HELPERS
 
@@ -161,17 +178,17 @@ public:
 //==== OVERLOAD of nsIFrame
   virtual nsIAtom* GetType() const;
 
   /** handler for attribute changes to mContent */
   NS_IMETHOD AttributeChanged(PRInt32         aNameSpaceID,
                               nsIAtom*        aAttribute,
                               PRInt32         aModType);
 
-  NS_IMETHOD GetText(nsString* aText);
+  nsresult GetText(nsString& aText);
 
   NS_DECL_QUERYFRAME
 
 public: //for methods who access nsTextControlFrame directly
   /**
    * Find out whether this is a single line text control.  (text or password)
    * @return whether this is a single line text control
    */
@@ -208,16 +225,17 @@ public: //for methods who access nsTextC
 
   /* called to free up native keybinding services */
   static NS_HIDDEN_(void) ShutDown();
 
   // called by the focus listener
   nsresult MaybeBeginSecureKeyboardInput();
   void MaybeEndSecureKeyboardInput();
 
+  void ClearValueCache() { mCachedValue.Truncate(); }
 protected:
   class EditorInitializer;
   friend class EditorInitializer;
 
   class EditorInitializer : public nsRunnable {
   public:
     EditorInitializer(nsTextControlFrame* aFrame) :
       mWeakFrame(aFrame),
@@ -308,17 +326,17 @@ protected:
   // for <textarea>).
   nsresult CalcIntrinsicSize(nsIRenderingContext* aRenderingContext,
                              nsSize&              aIntrinsicSize);
 
 private:
   //helper methods
   nsresult SetSelectionInternal(nsIDOMNode *aStartNode, PRInt32 aStartOffset,
                                 nsIDOMNode *aEndNode, PRInt32 aEndOffset);
-  nsresult SelectAllContents();
+  nsresult SelectAllOrCollapseToEndOfText(PRBool aSelect);
   nsresult SetSelectionEndPoints(PRInt32 aSelStart, PRInt32 aSelEnd);
   
 private:
   nsCOMPtr<nsIContent> mAnonymousDiv;
 
   nsCOMPtr<nsIEditor> mEditor;
 
   // these packed bools could instead use the high order bits on mState, saving 4 bytes 
@@ -330,13 +348,15 @@ private:
   // eventually) when mFireChangeEventState==true, this is used by nsFileControlFrame.
   PRPackedBool mFireChangeEventState;
   PRPackedBool mInSecureKeyboardInputMode;
 
   nsRefPtr<nsTextInputSelectionImpl> mSelCon;
   nsCOMPtr<nsFrameSelection> mFrameSel;
   nsTextInputListener* mTextListener;
   nsString mFocusedValue;
+  nsString mCachedValue; // Caches non-hard-wrapped value on a multiline control.
+  nsRefPtr<nsAnonDivObserver> mMutationObserver;
 };
 
 #endif
 
 
--- a/layout/generic/nsGfxScrollFrame.cpp
+++ b/layout/generic/nsGfxScrollFrame.cpp
@@ -74,16 +74,17 @@
 #include "nsContentUtils.h"
 #include "nsLayoutUtils.h"
 #ifdef ACCESSIBILITY
 #include "nsIAccessibilityService.h"
 #endif
 #include "nsDisplayList.h"
 #include "nsBidiUtils.h"
 #include "nsFrameManager.h"
+#include "nsIPrefService.h"
 
 //----------------------------------------------------------------------
 
 //----------nsHTMLScrollFrame-------------------------------------------
 
 nsIFrame*
 NS_NewHTMLScrollFrame(nsIPresShell* aPresShell, nsStyleContext* aContext, PRBool aIsRoot)
 {
--- a/layout/generic/nsImageFrame.cpp
+++ b/layout/generic/nsImageFrame.cpp
@@ -1753,18 +1753,17 @@ NS_IMPL_ISUPPORTS2(nsImageFrame::IconLoa
 
 static const char kIconLoadPrefs[][40] = {
   "browser.display.force_inline_alttext",
   "browser.display.show_image_placeholders"
 };
 
 nsImageFrame::IconLoad::IconLoad()
 {
-  nsCOMPtr<nsIPrefBranch2> prefBranch =
-    do_QueryInterface(nsContentUtils::GetPrefBranch());
+  nsIPrefBranch2* prefBranch = nsContentUtils::GetPrefBranch();
 
   // register observers
   for (PRUint32 i = 0; i < NS_ARRAY_LENGTH(kIconLoadPrefs); ++i)
     prefBranch->AddObserver(kIconLoadPrefs[i], this, PR_FALSE);
 
   GetPrefs();
 }
 
--- a/layout/generic/nsImageMap.cpp
+++ b/layout/generic/nsImageMap.cpp
@@ -216,39 +216,39 @@ void Area::ParseCoords(const nsAString& 
        * Skip to the end of the separator, noting if we have a
        * comma.
        */
       has_comma = PR_FALSE;
       while (is_space(*tptr) || *tptr == ',')
       {
         if (*tptr == ',')
         {
-          if (has_comma == PR_FALSE)
+          if (!has_comma)
           {
             has_comma = PR_TRUE;
           }
           else
           {
             break;
           }
         }
         tptr++;
       }
       /*
        * If this was trailing whitespace we skipped, we are done.
        */
-      if ((*tptr == '\0')&&(has_comma == PR_FALSE))
+      if ((*tptr == '\0') && !has_comma)
       {
         break;
       }
       /*
        * Else if the separator is all whitespace, and this is not the
        * end of the string, add a comma to the separator.
        */
-      else if (has_comma == PR_FALSE)
+      else if (!has_comma)
       {
         *n_str = ',';
       }
 
       /*
        * count the entry skipped.
        */
       cnt++;
--- a/layout/generic/nsObjectFrame.cpp
+++ b/layout/generic/nsObjectFrame.cpp
@@ -168,17 +168,17 @@ static NS_DEFINE_CID(kAppShellCID, NS_AP
 #ifdef MOZ_X11
 #include <X11/Xlib.h>
 /* X headers suck */
 enum { XKeyPress = KeyPress };
 #ifdef KeyPress
 #undef KeyPress
 #endif
 
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO == 5)
 #define MOZ_COMPOSITED_PLUGINS 1
 
 #include "gfxXlibSurface.h"
 
 #include <X11/Xutil.h>
 #include <X11/Xatom.h>
 #include <X11/extensions/XShm.h>
 #include <sys/ipc.h>
@@ -411,17 +411,17 @@ public:
 #endif
   }
 
   PRBool MatchPluginName(const char *aPluginName)
   {
     return strncmp(GetPluginName(), aPluginName, strlen(aPluginName)) == 0;
   }
 
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO == 5)
   nsresult SetAbsoluteScreenPosition(nsIDOMElement* element,
                                      nsIDOMClientRect* position,
                                      nsIDOMClientRect* clip);
 #endif
 
 private:
   void FixUpURLS(const nsString &name, nsAString &value);
 
@@ -506,17 +506,17 @@ private:
   private:
     NPWindow* mWindow;
     nsIPluginInstance* mInstance;
     const nsIntSize& mPluginSize;
     const nsIntRect& mDirtyRect;
   };
 #endif
 
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO == 5)
 
   // On hildon, we attempt to use NPImageExpose which allows us faster
   // painting.
 
   // used to keep track of how big our buffer is.
   nsIntSize mPluginSize;
 
   // The absolute position on the screen to draw to.
@@ -1220,17 +1220,17 @@ nsObjectFrame::ComputeWidgetGeometry(con
   }
 }
 
 nsresult
 nsObjectFrame::SetAbsoluteScreenPosition(nsIDOMElement* element,
                                          nsIDOMClientRect* position,
                                          nsIDOMClientRect* clip)
 {
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO == 5)
   if (!mInstanceOwner)
     return NS_ERROR_NOT_AVAILABLE;
   return mInstanceOwner->SetAbsoluteScreenPosition(element, position, clip);
 #else
   return NS_ERROR_NOT_IMPLEMENTED;
 #endif
 }
 
@@ -2132,17 +2132,17 @@ GetMIMEType(nsIPluginInstance *aPluginIn
   }
   return "";
 }
 #endif
 
 static PRBool
 DoDelayedStop(nsPluginInstanceOwner *aInstanceOwner, PRBool aDelayedStop)
 {
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO==5)
   // Don't delay stop on Maemo/Hildon (bug 530739).
   if (aDelayedStop && aInstanceOwner->MatchPluginName("Shockwave Flash"))
     return PR_FALSE;
 #endif
 
   // Don't delay stopping QuickTime (bug 425157), Flip4Mac (bug 426524),
   // XStandard (bug 430219), CMISS Zinc (bug 429604).
   if (aDelayedStop
@@ -2450,17 +2450,17 @@ nsPluginInstanceOwner::nsPluginInstanceO
   mCachedAttrParamNames = nsnull;
   mCachedAttrParamValues = nsnull;
   mDestroyWidget = PR_FALSE;
 
 #ifdef MOZ_COMPOSITED_PLUGINS
   mLastPoint = nsIntPoint(0,0);
 #endif
 
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO == 5)
   mPluginSize = nsIntSize(0,0);
   mXlibSurfGC = None;
   mBlitWindow = nsnull;
   mSharedXImage = nsnull;
   mSharedSegmentInfo.shmaddr = nsnull;
 #endif
 
 #ifdef XP_MACOSX
@@ -2520,17 +2520,17 @@ nsPluginInstanceOwner::~nsPluginInstance
     ph->DeletePluginNativeWindow(mPluginWindow);
     mPluginWindow = nsnull;
   }
 
   if (mInstance) {
     mInstance->InvalidateOwner();
   }
 
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO == 5)
   ReleaseXShm();
 #endif
 }
 
 /*
  * nsISupports Implementation
  */
 
@@ -2732,17 +2732,17 @@ NS_IMETHODIMP nsPluginInstanceOwner::Get
   return NS_OK;
 }
 
 NS_IMETHODIMP nsPluginInstanceOwner::InvalidateRect(NPRect *invalidRect)
 {
   if (!mObjectFrame || !invalidRect || !mWidgetVisible)
     return NS_ERROR_FAILURE;
 
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO == 5)
   PRBool simpleImageRender = PR_FALSE;
   mInstance->GetValueFromPlugin(NPPVpluginWindowlessLocalBool,
                                 &simpleImageRender);
   if (simpleImageRender) {  
     NativeImageDraw(invalidRect);
     return NS_OK;
   }
 #endif
@@ -2859,16 +2859,28 @@ NS_IMETHODIMP nsPluginInstanceOwner::Get
   GdkWindow* gdkWindow = static_cast<GdkWindow*>(win->GetNativeData(NS_NATIVE_WINDOW));
   if (!gdkWindow)
     return NS_ERROR_FAILURE;
   gdkWindow = gdk_window_get_toplevel(gdkWindow);
 #ifdef MOZ_X11
   *static_cast<Window*>(value) = GDK_WINDOW_XID(gdkWindow);
 #endif
   return NS_OK;
+#elif defined(MOZ_WIDGET_QT)
+  // X11 window managers want the toplevel window for WM_TRANSIENT_FOR.
+  nsIWidget* win = mObjectFrame->GetWindow();
+  if (!win)
+    return NS_ERROR_FAILURE;
+  QWidget* widget = static_cast<QWidget*>(win->GetNativeData(NS_NATIVE_WINDOW));
+  if (!widget)
+    return NS_ERROR_FAILURE;
+#ifdef MOZ_X11
+  *static_cast<Window*>(value) = widget->handle();
+#endif
+  return NS_OK;
 #else
   return NS_ERROR_NOT_IMPLEMENTED;
 #endif
 }
 
 NS_IMETHODIMP nsPluginInstanceOwner::SetEventModel(PRInt32 eventModel)
 {
 #ifdef XP_MACOSX
@@ -4866,17 +4878,17 @@ void nsPluginInstanceOwner::Paint(const 
 #if defined(MOZ_X11) || defined(MOZ_DFB)
 void nsPluginInstanceOwner::Paint(gfxContext* aContext,
                                   const gfxRect& aFrameRect,
                                   const gfxRect& aDirtyRect)
 {
   if (!mInstance || !mObjectFrame)
     return;
 
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO == 5)
   // through to be able to paint the context passed in.  This allows
   // us to handle plugins that do not self invalidate (slowly, but
   // accurately), and it allows us to reduce flicker.
   PRBool simpleImageRender = PR_FALSE;
   mInstance->GetValueFromPlugin(NPPVpluginWindowlessLocalBool,
                                 &simpleImageRender);
   if (simpleImageRender) {
     gfxMatrix matrix = aContext->CurrentMatrix();
@@ -4955,17 +4967,17 @@ DepthOfVisual(const Screen* screen, cons
     }
   }
 
   NS_ERROR("Visual not on Screen.");
   return 0;
 }
 #endif
 
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO == 5)
 
 static GdkWindow* GetClosestWindow(nsIDOMElement *element)
 {
   nsCOMPtr<nsIContent> content = do_QueryInterface(element);
   nsIFrame* frame = content->GetPrimaryFrame();
   if (!frame)
     return nsnull;
 
@@ -5646,17 +5658,17 @@ NS_IMETHODIMP nsPluginInstanceOwner::Cre
   return rv;
 }
 
 void nsPluginInstanceOwner::SetPluginHost(nsIPluginHost* aHost)
 {
   mPluginHost = aHost;
 }
 
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO == 5)
 PRBool nsPluginInstanceOwner::UpdateVisibility(PRBool aVisible)
 {
   // NOTE: Death grip must be held by caller.
   if (!mInstance)
     return PR_TRUE;
 
   PRBool handled;
   NPEvent pluginEvent;
@@ -5810,17 +5822,17 @@ void nsPluginInstanceOwner::FixUpURLS(co
     nsCOMPtr<nsIURI> baseURI = mContent->GetBaseURI();
     nsAutoString newURL;
     NS_MakeAbsoluteURI(newURL, value, baseURI);
     if (!newURL.IsEmpty())
       value = newURL;
   }
 }
 
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO == 5)
 nsresult
 nsPluginInstanceOwner::SetAbsoluteScreenPosition(nsIDOMElement* element,
                                                  nsIDOMClientRect* position,
                                                  nsIDOMClientRect* clip)
 {
   if (!element || !position || !clip)
     return NS_ERROR_FAILURE;
   
--- a/layout/generic/nsQueryFrame.h
+++ b/layout/generic/nsQueryFrame.h
@@ -106,29 +106,27 @@ public:
     nsHTMLCanvasFrame_id,
     nsHTMLContainerFrame_id,
     nsHTMLFramesetBlankFrame_id,
     nsHTMLFramesetBorderFrame_id,
     nsHTMLFramesetFrame_id,
     nsHTMLScrollFrame_id,
     nsIAnonymousContentCreator_id,
     nsICSSPseudoComparator_id,
-    nsICheckboxControlFrame_id,
     nsIComboboxControlFrame_id,
     nsIFormControlFrame_id,
     nsIFrame_id,
     nsIFrameFrame_id,
     nsIImageFrame_id,
     nsIListControlFrame_id,
     nsIMathMLFrame_id,
     nsIMenuFrame_id,
     nsIObjectFrame_id,
     nsIPageSequenceFrame_id,
     nsIPercentHeightObserver_id,
-    nsIRadioControlFrame_id,
     nsIRootBox_id,
     nsISVGChildFrame_id,
     nsISVGGlyphFragmentLeaf_id,
     nsISVGGlyphFragmentNode_id,
     nsISVGSVGFrame_id,
     nsIScrollableFrame_id,
     nsIScrollbarFrame_id,
     nsIScrollbarMediator_id,
new file mode 100644
--- /dev/null
+++ b/layout/reftests/bugs/503399-ref.html
@@ -0,0 +1,33 @@
+<!DOCTYPE HTML>
+<html class="reftest-wait"><head>
+    <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
+    <title>Testcase for bug 503399</title>
+    <style type="text/css">
+
+        html,body {
+            color:black; background-color:white; font-size:16px;
+        }
+	p {
+            max-width:200px;
+            height: 1em;
+            overflow:hidden;
+        }
+    </style>
+    <script>
+      function runTest(p) {
+        try {
+          var r = window.getSelection().getRangeAt(0);
+          r.setStart(p.childNodes[1],1);
+          r.setEnd(p.childNodes[1],1);
+        } catch (e) {}
+        document.documentElement.removeAttribute('class');
+      }
+    </script>
+</head>
+<body onload="setTimeout(function(){window.focus();document.getElementsByTagName('p')[0].focus()},400)">
+
+<p onfocus="runTest(this)" contentEditable="true"
+   style="text-align:justify"><span>mm mm mm mm m</span>m mm mm</p>
+
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/reftests/bugs/503399.html
@@ -0,0 +1,33 @@
+<!DOCTYPE HTML>
+<html class="reftest-wait"><head>
+    <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
+    <title>Testcase for bug 503399</title>
+    <style type="text/css">
+
+        html,body {
+            color:black; background-color:white; font-size:16px;
+        }
+	p {
+            max-width:200px;
+            height: 1em;
+            overflow:hidden;
+        }
+    </style>
+    <script>
+      function runTest(p) {
+        try {
+          var r = window.getSelection().getRangeAt(0);
+          r.setStart(p.childNodes[0],14);
+          r.setEnd(p.childNodes[0],14);
+        } catch (e) {}
+        document.documentElement.removeAttribute('class');
+      }
+    </script>
+</head>
+<body onload="setTimeout(function(){window.focus();document.getElementsByTagName('p')[0].focus()},400)">
+
+<p onfocus="runTest(this)" contentEditable="true"
+   style="text-align:justify">mm mm mm mm mm mm mm</p>
+
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/reftests/bugs/503531-1-ref.html
@@ -0,0 +1,23 @@
+<html class="reftest-wait"><head>
+    <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
+    <title>Testcase #1 for bug 503531</title>
+<script>
+function boom() {
+  var caret = document.getElementById('caret');
+
+  var sel = window.getSelection();
+  sel.removeAllRanges();
+  var range = document.createRange();
+  range.selectNode(caret);
+  sel.addRange(range);
+  sel.collapseToStart();
+
+  setTimeout(function(){document.documentElement.className = '';}, 50)
+}
+</script>
+</head>
+<body contenteditable="true" onload="document.body.focus(); boom()">
+<div>BLOCK</div>
+<div id="caret"></div>
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/reftests/bugs/503531-1.html
@@ -0,0 +1,25 @@
+<html class="reftest-wait"><head>
+    <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
+    <title>Testcase #1 for bug 503531</title>
+<script>
+function boom() {
+  var emptyText = document.createTextNode('x');
+  document.body.appendChild(emptyText);
+
+  var sel = window.getSelection();
+  sel.removeAllRanges();
+  var range = document.createRange();
+  range.selectNode(emptyText);
+  sel.addRange(range);
+  sel.collapseToStart();
+
+  emptyText.nodeValue='';
+  
+  setTimeout(function(){document.documentElement.className = '';}, 50)
+}
+</script>
+</head>
+<body contenteditable="true" onload="document.body.focus(); boom()">
+<div>BLOCK</div>
+</body>
+</html>
--- a/layout/reftests/bugs/reftest.list
+++ b/layout/reftests/bugs/reftest.list
@@ -1318,16 +1318,18 @@ fails-if(MOZ_WIDGET_TOOLKIT!="cocoa") ==
 == 501257-1.xhtml 501257-1-ref.xhtml
 == 501627-1.html 501627-1-ref.html
 == 502288-1.html 502288-1-ref.html
 == 502942-1.html 502942-1-ref.html
 == 502447-1.html 502447-1-ref.html
 == 502795-1.html 502795-1-ref.html
 == 503364-1a.html 503364-1-ref.html
 == 503364-1b.html 503364-1-ref.html
+== 503399.html 503399-ref.html
+== 503531-1.html 503531-1-ref.html
 == 504032-1.html 504032-1-ref.html
 == 505743-1.html about:blank
 == 506481-1.html 506481-1-ref.html
 == 507187-1.html 507187-1-ref.html
 == 507487-1.html 507487-1-ref.html
 == 507487-2.xhtml 507487-2-ref.xhtml
 == 507762-1.html 507762-1-ref.html
 == 507762-2.html 507762-2-ref.html
new file mode 100644
--- /dev/null
+++ b/layout/reftests/svg/objectBoundingBox-and-fePointLight-01-ref.svg
@@ -0,0 +1,22 @@
+<!--
+     Any copyright is dedicated to the Public Domain.
+     http://creativecommons.org/licenses/publicdomain/
+-->
+<svg width="100%" height="100%"
+  viewBox="0 0 480 360" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
+  <title>Reference for objectBoundingBox with fePointLight</title>
+  <!-- From https://bugzilla.mozilla.org/show_bug.cgi?id=544742 -->
+
+  <defs>
+    <filter id="light" primitiveUnits="userSpaceOnUse">
+      <feSpecularLighting lighting-color="blue" surfaceScale="5" specularConstant="10" specularExponent="6">
+        <fePointLight x="30" y="30" z="-5"/>
+      </feSpecularLighting>
+      <feComposite operator="in" in2="SourceGraphic"/>
+    </filter>
+  </defs>
+
+  <rect x="20" y="20" width="40" height="20" filter="url(#light)" fill="black" />
+
+</svg>
+
new file mode 100644
--- /dev/null
+++ b/layout/reftests/svg/objectBoundingBox-and-fePointLight-01.svg
@@ -0,0 +1,24 @@
+<!--
+     Any copyright is dedicated to the Public Domain.
+     http://creativecommons.org/licenses/publicdomain/
+-->
+<svg width="100%" height="100%"
+  viewBox="0 0 480 360" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
+  <title>Testcase for objectBoundingBox with fePointLight</title>
+  <!-- From https://bugzilla.mozilla.org/show_bug.cgi?id=544742 -->
+
+  <defs>
+    <filter id="light" primitiveUnits="objectBoundingBox">
+      <feSpecularLighting lighting-color="blue" surfaceScale="5" specularConstant="10" specularExponent="6">
+        <!-- Note: for z  the scalefactor is  31,622776601683793319988935444327
+                     sqrt(bbox.width*bbox.width + bbox.height*bbox.height)/sqrt(2) -->
+        <fePointLight x="0.75" y="1.5" z="-0.15811388300841896659994467722167"/>
+      </feSpecularLighting>
+      <feComposite operator="in" in2="SourceGraphic"/>
+    </filter>
+  </defs>
+
+  <rect x="20" y="20" width="40" height="20" filter="url(#light)" fill="black" />
+
+</svg>
+
--- a/layout/reftests/svg/reftest.list
+++ b/layout/reftests/svg/reftest.list
@@ -91,16 +91,17 @@ fails == inline-in-xul-basic-01.xul pass
 == linearGradient-basic-02.svg pass.svg
 == markers-and-group-opacity-01.svg markers-and-group-opacity-01-ref.svg
 == marker-attribute-01.svg pass.svg
 == mask-containing-masked-content-01.svg pass.svg
 # Bug 456323
 # == mask-transformed-01.svg mask-transformed-01-ref.svg
 == nested-viewBox-01.svg pass.svg
 == objectBoundingBox-and-clipPath.svg pass.svg
+== objectBoundingBox-and-fePointLight-01.svg objectBoundingBox-and-fePointLight-01-ref.svg
 == objectBoundingBox-and-mask.svg pass.svg
 == objectBoundingBox-and-pattern-01a.svg objectBoundingBox-and-pattern-01-ref.svg
 == objectBoundingBox-and-pattern-01b.svg objectBoundingBox-and-pattern-01-ref.svg
 == objectBoundingBox-and-pattern-01c.svg objectBoundingBox-and-pattern-01-ref.svg
 fails-if(http.oscpu.match(/Mac\x20OS\x20X\x2010\.4$/)) == opacity-and-gradient-01.svg pass.svg # fails on OS X 10.4 (bug 379610)
 == opacity-and-gradient-02.svg opacity-and-gradient-02-ref.svg
 == opacity-and-pattern-01.svg pass.svg
 == path-01.svg path-01-ref.svg
new file mode 100644
--- /dev/null
+++ b/layout/reftests/svg/smil/anim-svg-preserveAspectRatio-01.svg
@@ -0,0 +1,38 @@
+<svg xmlns="http://www.w3.org/2000/svg"
+     xmlns:xlink="http://www.w3.org/1999/xlink"
+     class="reftest-wait"
+     onload="setTimeAndSnapshot(1, true)">
+  <title>Test animation of the "preserveAspectRatio" attribute on the "svg" element</title>
+  <script xlink:href="smil-util.js" type="text/javascript"/>
+  <rect width="100%" height="100%" fill="lime"/>
+
+  <!-- 40% through animation simple duration -
+       tests that the animation doesn't affect the element too early -->
+  <svg width="100" height="50" viewBox="0 0 100 100"
+       preserveAspectRatio="xMidYMid meet">
+    <!-- this should change the referencing element at 1.25s,
+         causing the red rect to stretch to fill its whole viewport -->
+    <animate attributeName="preserveAspectRatio"
+             calcMode="discrete"
+             begin="0s" dur="2.5s"
+             to="xMidYMid slice"
+             fill="freeze"/>
+    <rect width="100%" height="100%" fill="red"/>
+  </svg>
+  <rect x="25" width="50" height="50" fill="lime"/>
+
+  <!-- 50% through animation simple duration -
+       tests that the animation affects the element now -->
+  <rect y="50" width="100" height="50" fill="red"/>
+  <svg y="50" width="100" height="50" viewBox="0 0 100 100"
+       preserveAspectRatio="xMidYMid meet">
+    <!-- this should change the referencing element at 1s,
+         causing the lime rect to stretch to fill its whole viewport -->
+    <animate attributeName="preserveAspectRatio"
+             calcMode="discrete"
+             begin="0s" dur="2s"
+             to="xMidYMid slice"
+             fill="freeze"/>
+    <rect width="100%" height="100%" fill="lime"/>
+  </svg>
+</svg>
--- a/layout/reftests/svg/smil/reftest.list
+++ b/layout/reftests/svg/smil/reftest.list
@@ -83,16 +83,19 @@ fails == anim-fillopacity-1xml.svg  anim
 
 # animate some enumeration attributes:
 == anim-feComposite-operator-01.svg lime.svg
 == anim-filter-filterUnits-01.svg lime.svg
 
 # animate some boolean attributes:
 == anim-feConvolveMatrix-preserveAlpha-01.svg lime.svg
 
+# animate some preserveAspectRatio attributes
+== anim-svg-preserveAspectRatio-01.svg lime.svg
+
 == anim-remove-1.svg anim-standard-ref.svg
 == anim-remove-2.svg anim-standard-ref.svg
 == anim-remove-3.svg anim-standard-ref.svg
 == anim-remove-4.svg anim-standard-ref.svg
 == anim-remove-5.svg anim-standard-ref.svg
 == anim-remove-6.svg anim-standard-ref.svg
 == anim-remove-7.svg anim-standard-ref.svg
 == anim-remove-8css.svg anim-standard-ref.svg
--- a/layout/reftests/text/reftest.list
+++ b/layout/reftests/text/reftest.list
@@ -49,8 +49,10 @@ random-if(MOZ_WIDGET_TOOLKIT=="cocoa") H
 HTTP(..) == zwnj-02.xhtml zwnj-02-ref.xhtml # HTTP(..) for ../filters.svg
 random-if(MOZ_WIDGET_TOOLKIT=="gtk2") != zwnj-01.html zwnj-01-notref.html # Bad fonts on the tinderbox -- works locally
 fails-if(MOZ_WIDGET_TOOLKIT=="windows") == cgj-01.html cgj-01-ref.html # bug 455455
 == 444656.html 444656-ref.html
 == 449555-1.html 449555-1-ref.html
 random HTTP(..) == 475092-sub.html 475092-ref.html # 482596
 random HTTP(..) == 475092-pos.html 475092-sub.html # 482596
 == 476378-soft-hyphen-fallback.html 476378-soft-hyphen-fallback-ref.html
+# Bug 484954
+== rgba-text.html rgba-text-ref.html
new file mode 100644
--- /dev/null
+++ b/layout/reftests/text/rgba-text-ref.html
@@ -0,0 +1,7 @@
+<!DOCTYPE HTML>
+<html>
+<body style="background: #000">
+	<!-- A regular old red box -->
+	<div style="background: red; position:absolute; top:30px; left:0px; padding:50px"></div>
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/reftests/text/rgba-text.html
@@ -0,0 +1,12 @@
+<!DOCTYPE HTML>
+<html>
+<body style="background: #000">
+	<div style="color: rgba(255, 255, 255, 0.2); font-size:48px;">_</div>
+	<!-- the red box should totally obscure the drawn portion of the text
+	     however if the text is painted as a box instead of an underscore it
+	     will show above the top of the red box.
+	     This test would have caught bug 484954
+	     -->
+	<div style="background: red; position:absolute; top:30px; left:0px; padding:50px"></div>
+</body>
+</html>
--- a/layout/style/nsCSSParser.cpp
+++ b/layout/style/nsCSSParser.cpp
@@ -1353,17 +1353,17 @@ CSSParserImpl::GetURLInParens(nsString& 
   }
 
   return PR_TRUE;
 }
 
 void
 CSSParserImpl::UngetToken()
 {
-  NS_PRECONDITION(mHavePushBack == PR_FALSE, "double pushback");
+  NS_PRECONDITION(!mHavePushBack, "double pushback");
   mHavePushBack = PR_TRUE;
 }
 
 PRBool
 CSSParserImpl::ExpectSymbol(PRUnichar aSymbol,
                             PRBool aSkipWS)
 {
   if (!GetToken(aSkipWS)) {
--- a/layout/style/nsCSSPseudoClassList.h
+++ b/layout/style/nsCSSPseudoClassList.h
@@ -109,16 +109,18 @@ CSS_STATE_PSEUDO_CLASS(mozSuppressed, ":
                        NS_EVENT_STATE_SUPPRESSED)
 CSS_STATE_PSEUDO_CLASS(mozLoading, ":-moz-loading", NS_EVENT_STATE_LOADING)
 CSS_STATE_PSEUDO_CLASS(mozTypeUnsupported, ":-moz-type-unsupported",
                        NS_EVENT_STATE_TYPE_UNSUPPORTED)
 CSS_STATE_PSEUDO_CLASS(mozHandlerDisabled, ":-moz-handler-disabled",
                        NS_EVENT_STATE_HANDLER_DISABLED)
 CSS_STATE_PSEUDO_CLASS(mozHandlerBlocked, ":-moz-handler-blocked",
                        NS_EVENT_STATE_HANDLER_BLOCKED)
+CSS_STATE_PSEUDO_CLASS(mozHandlerCrashed, ":-moz-handler-crashed",
+                       NS_EVENT_STATE_HANDLER_CRASHED)
 
 CSS_PSEUDO_CLASS(mozHasHandlerRef, ":-moz-has-handlerref")
 
 // Match nodes that are HTML but not XHTML
 CSS_PSEUDO_CLASS(mozIsHTML, ":-moz-is-html")
 
 // Matches anything when the specified look-and-feel metric is set
 CSS_PSEUDO_CLASS(mozSystemMetric, ":-moz-system-metric")
--- a/layout/style/test/test_selectors.html
+++ b/layout/style/test/test_selectors.html
@@ -699,16 +699,23 @@ function run() {
     test_parseable("::-moz-tree-row(selected,focus)");
     test_parseable(":-moz-tree-row(selected     focus)");
     test_parseable("::-moz-tree-row(selected    ,   focus)");
     test_parseable("::-moz-tree-twisty(  hover open  )");
     test_balanced_unparseable("::-moz-tree-row(selected {[]} )");
     test_balanced_unparseable(":-moz-tree-twisty(open())");
     test_balanced_unparseable("::-moz-tree-twisty(hover ())");
 
+    // Plugin pseudoclasses
+    test_parseable(":-moz-type-unsupported");
+    test_parseable(":-moz-handler-disabled");
+    test_parseable(":-moz-handler-blocked");
+    test_parseable(":-moz-handler-crashed");
+    test_parseable(":-moz-has-handlerref");
+
     // Case sensitivity of tag selectors
     function setup_cased_spans(body) {
       var data = [
         { tag: "span" },
         { tag: "sPaN" },
         { tag: "Span" },
         { tag: "SPAN" },
         { ns: "http://www.w3.org/1999/xhtml", tag: "span" },
--- a/layout/svg/base/src/nsSVGClipPathFrame.h
+++ b/layout/svg/base/src/nsSVGClipPathFrame.h
@@ -94,17 +94,17 @@ public:
   // automatically sets and clears the mInUse flag on the clip path frame
   // (to prevent nasty reference loops). It's easy to mess this up
   // and break things, so this helper makes the code far more robust.
   class AutoClipPathReferencer
   {
   public:
     AutoClipPathReferencer(nsSVGClipPathFrame *aFrame)
        : mFrame(aFrame) {
-      NS_ASSERTION(mFrame->mInUse == PR_FALSE, "reference loop!");
+      NS_ASSERTION(!mFrame->mInUse, "reference loop!");
       mFrame->mInUse = PR_TRUE;
     }
     ~AutoClipPathReferencer() {
       mFrame->mInUse = PR_FALSE;
     }
   private:
     nsSVGClipPathFrame *mFrame;
   };
--- a/layout/svg/base/src/nsSVGFilterInstance.cpp
+++ b/layout/svg/base/src/nsSVGFilterInstance.cpp
@@ -64,16 +64,27 @@ nsSVGFilterInstance::GetPrimitiveLength(
   case nsSVGUtils::XY:
   default:
     return value *
       sqrt(Square(mFilterSpaceSize.width) + Square(mFilterSpaceSize.height)) /
       sqrt(Square(mFilterRect.Width()) + Square(mFilterRect.Height()));
   }
 }
 
+void
+nsSVGFilterInstance::ConvertLocation(float aValues[3]) const
+{
+  if (mPrimitiveUnits == nsIDOMSVGUnitTypes::SVG_UNIT_TYPE_OBJECTBOUNDINGBOX) {
+    aValues[0] *= mTargetBBox.Width();
+    aValues[1] *= mTargetBBox.Height();
+    aValues[2] *= nsSVGUtils::ComputeNormalizedHypotenuse(
+                    mTargetBBox.Width(), mTargetBBox.Height());
+  }
+}
+
 already_AddRefed<gfxImageSurface>
 nsSVGFilterInstance::CreateImage()
 {
   nsRefPtr<gfxImageSurface> surface =
     new gfxImageSurface(gfxIntSize(mSurfaceRect.width, mSurfaceRect.height),
                         gfxASurface::ImageFormatARGB32);
 
   if (!surface || surface->CairoStatus())
--- a/layout/svg/base/src/nsSVGFilterInstance.h
+++ b/layout/svg/base/src/nsSVGFilterInstance.h
@@ -60,16 +60,17 @@ struct gfxRect;
  * We build a graph of the filter image data flow, essentially
  * converting the filter graph to SSA. This lets us easily propagate
  * analysis data (such as bounding-boxes) over the filter primitive graph.
  */
 class NS_STACK_CLASS nsSVGFilterInstance
 {
 public:
   float GetPrimitiveLength(nsSVGLength2 *aLength) const;
+  void ConvertLocation(float aValues[3]) const;
 
   nsSVGFilterInstance(nsIFrame *aTargetFrame,
                       nsSVGFilterPaintCallback *aPaintCallback,
                       nsSVGFilterElement *aFilterElement,
                       const gfxRect &aTargetBBox,
                       const gfxRect& aFilterRect,
                       const nsIntSize& aFilterSpaceSize,
                       const gfxMatrix &aFilterSpaceToDeviceSpaceTransform,
--- a/layout/svg/base/src/nsSVGImageFrame.cpp
+++ b/layout/svg/base/src/nsSVGImageFrame.cpp
@@ -197,17 +197,18 @@ nsSVGImageFrame::GetImageTransform()
   nsSVGImageElement *element = static_cast<nsSVGImageElement*>(mContent);
   element->GetAnimatedLengthValues(&x, &y, &width, &height, nsnull);
 
   PRInt32 nativeWidth, nativeHeight;
   mImageContainer->GetWidth(&nativeWidth);
   mImageContainer->GetHeight(&nativeHeight);
 
   gfxMatrix viewBoxTM =
-    nsSVGUtils::GetViewBoxTransform(width, height,
+    nsSVGUtils::GetViewBoxTransform(element,
+                                    width, height,
                                     0, 0, nativeWidth, nativeHeight,
                                     element->mPreserveAspectRatio);
 
   return viewBoxTM * gfxMatrix().Translate(gfxPoint(x, y)) * GetCanvasTM();
 }
 
 //----------------------------------------------------------------------
 // nsISVGChildFrame methods:
--- a/layout/svg/base/src/nsSVGMaskFrame.h
+++ b/layout/svg/base/src/nsSVGMaskFrame.h
@@ -89,17 +89,17 @@ private:
   // automatically sets and clears the mInUse flag on the mask frame
   // (to prevent nasty reference loops). It's easy to mess this up
   // and break things, so this helper makes the code far more robust.
   class AutoMaskReferencer
   {
   public:
     AutoMaskReferencer(nsSVGMaskFrame *aFrame)
        : mFrame(aFrame) {
-      NS_ASSERTION(mFrame->mInUse == PR_FALSE, "reference loop!");
+      NS_ASSERTION(!mFrame->mInUse, "reference loop!");
       mFrame->mInUse = PR_TRUE;
     }
     ~AutoMaskReferencer() {
       mFrame->mInUse = PR_FALSE;
     }
   private:
     nsSVGMaskFrame *mFrame;
   };
--- a/layout/svg/base/src/nsSVGPatternFrame.cpp
+++ b/layout/svg/base/src/nsSVGPatternFrame.cpp
@@ -454,16 +454,21 @@ nsSVGPatternFrame::GetReferencedPattern(
     return nsnull;
 
   return static_cast<nsSVGPatternFrame*>(result);
 }
 
 nsSVGPatternElement *
 nsSVGPatternFrame::GetPatternWithAttr(nsIAtom *aAttrName, nsIContent *aDefault)
 {
+  // XXX TODO: this method needs to take account of SMIL animation, since it
+  // the requested attribute may be animated even if it is not set in the DOM.
+  // The callers also need to be fixed up to then ask for the right thing from
+  // the pattern we return! Do we neet to call mContent->FlushAnimations()?
+
   if (mContent->HasAttr(kNameSpaceID_None, aAttrName))
     return static_cast<nsSVGPatternElement *>(mContent);
 
   nsSVGPatternElement *pattern = static_cast<nsSVGPatternElement *>(aDefault);
 
   nsSVGPatternFrame *next = GetReferencedPattern();
   if (!next)
     return pattern;
@@ -536,17 +541,20 @@ nsSVGPatternFrame::ConstructCTM(const gf
 
   gfxMatrix tm;
   const nsSVGViewBoxRect viewBox = GetViewBox().GetAnimValue();
 
   if (viewBox.height > 0.0f && viewBox.width > 0.0f) {
     nsSVGSVGElement *ctx = aTargetContent->GetCtx();
     float viewportWidth = GetWidth()->GetAnimValue(ctx);
     float viewportHeight = GetHeight()->GetAnimValue(ctx);
-    gfxMatrix viewBoxTM = nsSVGUtils::GetViewBoxTransform(viewportWidth, viewportHeight,
+    nsSVGPatternElement *patternElement =
+      static_cast<nsSVGPatternElement*>(mContent);
+    gfxMatrix viewBoxTM = nsSVGUtils::GetViewBoxTransform(patternElement,
+                                                          viewportWidth, viewportHeight,
                                                           viewBox.x, viewBox.y,
                                                           viewBox.width, viewBox.height,
                                                           GetPreserveAspectRatio(),
                                                           PR_TRUE);
 
     float refX = GetX()->GetAnimValue(ctx);
     float refY = GetY()->GetAnimValue(ctx);
     gfxPoint ref = viewBoxTM.Transform(gfxPoint(refX, refY));
--- a/layout/svg/base/src/nsSVGUtils.cpp
+++ b/layout/svg/base/src/nsSVGUtils.cpp
@@ -794,27 +794,28 @@ nsSVGUtils::GetOuterSVGFrameAndCoveredRe
   nsISVGChildFrame* svg = do_QueryFrame(aFrame);
   if (!svg)
     return nsnull;
   *aRect = svg->GetCoveredRegion();
   return GetOuterSVGFrame(aFrame);
 }
 
 gfxMatrix
-nsSVGUtils::GetViewBoxTransform(float aViewportWidth, float aViewportHeight,
+nsSVGUtils::GetViewBoxTransform(nsSVGElement* aElement,
+                                float aViewportWidth, float aViewportHeight,
                                 float aViewboxX, float aViewboxY,
                                 float aViewboxWidth, float aViewboxHeight,
                                 const nsSVGPreserveAspectRatio &aPreserveAspectRatio,
                                 PRBool aIgnoreAlign)
 {
   NS_ASSERTION(aViewboxWidth > 0, "viewBox width must be greater than zero!");
   NS_ASSERTION(aViewboxHeight > 0, "viewBox height must be greater than zero!");
 
-  PRUint16 align = aPreserveAspectRatio.GetAnimValue().GetAlign();
-  PRUint16 meetOrSlice = aPreserveAspectRatio.GetAnimValue().GetMeetOrSlice();
+  PRUint16 align = aPreserveAspectRatio.GetAnimValue(aElement).GetAlign();
+  PRUint16 meetOrSlice = aPreserveAspectRatio.GetAnimValue(aElement).GetMeetOrSlice();
 
   // default to the defaults
   if (align == nsIDOMSVGPreserveAspectRatio::SVG_PRESERVEASPECTRATIO_UNKNOWN)
     align = nsIDOMSVGPreserveAspectRatio::SVG_PRESERVEASPECTRATIO_XMIDYMID;
   if (meetOrSlice == nsIDOMSVGPreserveAspectRatio::SVG_MEETORSLICE_UNKNOWN)
     meetOrSlice = nsIDOMSVGPreserveAspectRatio::SVG_MEETORSLICE_MEET;
 
   // alignment disabled for this matrix setup
--- a/layout/svg/base/src/nsSVGUtils.h
+++ b/layout/svg/base/src/nsSVGUtils.h
@@ -339,17 +339,18 @@ public:
    * @return the outer SVG frame which aRect is relative to
    */
   static nsIFrame*
   GetOuterSVGFrameAndCoveredRegion(nsIFrame* aFrame, nsRect* aRect);
 
   /* Generate a viewbox to viewport tranformation matrix */
   
   static gfxMatrix
-  GetViewBoxTransform(float aViewportWidth, float aViewportHeight,
+  GetViewBoxTransform(nsSVGElement* aElement,
+                      float aViewportWidth, float aViewportHeight,
                       float aViewboxX, float aViewboxY,
                       float aViewboxWidth, float aViewboxHeight,
                       const nsSVGPreserveAspectRatio &aPreserveAspectRatio,
                       PRBool aIgnoreAlign = PR_FALSE);
 
   /* Paint SVG frame with SVG effects - aDirtyRect is the area being
    * redrawn, in device pixel coordinates relative to the outer svg */
   static void
--- a/layout/xul/base/src/nsPopupSetFrame.cpp
+++ b/layout/xul/base/src/nsPopupSetFrame.cpp
@@ -18,17 +18,17 @@
  * Netscape Communications Corporation.
  * Portions created by the Initial Developer are Copyright (C) 1998
  * the Initial Developer. All Rights Reserved.
  *
  * Contributor(s):
  *   Original Author: David W. Hyatt (hyatt@netscape.com)
  *   Pierre Phaneuf <pp@ludusdesign.com>
  *   Dean Tessman <dean_tessman@hotmail.com>
- *   Mats Palmgren <mats.palmgren@bredband.net>
+ *   Mats Palmgren <matspal@gmail.com>
  *
  * Alternatively, the contents of this file may be used under the terms of
  * either of the GNU General Public License Version 2 or later (the "GPL"),
  * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
  * in which case the provisions of the GPL or the LGPL are applicable instead
  * of those above. If you wish to allow use of your version of this file only
  * under the terms of either the GPL or the LGPL, and not to allow others to
  * use your version of this file under the terms of the MPL, indicate your
@@ -43,40 +43,18 @@
 #include "nsGkAtoms.h"
 #include "nsCOMPtr.h"
 #include "nsIContent.h"
 #include "nsPresContext.h"
 #include "nsStyleContext.h"
 #include "nsBoxLayoutState.h"
 #include "nsIScrollableFrame.h"
 #include "nsIRootBox.h"
-
-nsPopupFrameList::nsPopupFrameList(nsIContent* aPopupContent, nsPopupFrameList* aNext)
-:mNextPopup(aNext), 
- mPopupFrame(nsnull),
- mPopupContent(aPopupContent)
-{
-}
+#include "nsMenuPopupFrame.h"
 
-void nsPopupFrameList::Destroy(nsIFrame* aDestructRoot)
-{
-  if (mPopupFrame) {
-    nsIFrame* prevSib = mPopupFrame->GetPrevSibling();
-    if (prevSib)
-      prevSib->SetNextSibling(mPopupFrame->GetNextSibling());
-    mPopupFrame->SetNextSibling(nsnull);
-    mPopupFrame->DestroyFrom((aDestructRoot) ? aDestructRoot : mPopupFrame);
-  }
-}
-
-//
-// NS_NewPopupSetFrame
-//
-// Wrapper for creating a new menu popup container
-//
 nsIFrame*
 NS_NewPopupSetFrame(nsIPresShell* aPresShell, nsStyleContext* aContext)
 {
   return new (aPresShell) nsPopupSetFrame (aPresShell, aContext);
 }
 
 NS_IMPL_FRAMEARENA_HELPERS(nsPopupSetFrame)
 
@@ -103,61 +81,65 @@ nsPopupSetFrame::GetType() const
   return nsGkAtoms::popupSetFrame;
 }
 
 NS_IMETHODIMP
 nsPopupSetFrame::AppendFrames(nsIAtom*        aListName,
                               nsFrameList&    aFrameList)
 {
   if (aListName == nsGkAtoms::popupList) {
-    return AddPopupFrameList(aFrameList);
+    AddPopupFrameList(aFrameList);
+    return NS_OK;
   }
   return nsBoxFrame::AppendFrames(aListName, aFrameList);
 }
 
 NS_IMETHODIMP
 nsPopupSetFrame::RemoveFrame(nsIAtom*        aListName,
                              nsIFrame*       aOldFrame)
 {
   if (aListName == nsGkAtoms::popupList) {
-    return RemovePopupFrame(aOldFrame);
+    RemovePopupFrame(aOldFrame);
+    return NS_OK;
   }
   return nsBoxFrame::RemoveFrame(aListName, aOldFrame);
 }
 
 NS_IMETHODIMP
 nsPopupSetFrame::InsertFrames(nsIAtom*        aListName,
                               nsIFrame*       aPrevFrame,
                               nsFrameList&    aFrameList)
 {
   if (aListName == nsGkAtoms::popupList) {
-    return AddPopupFrameList(aFrameList);
+    AddPopupFrameList(aFrameList);
+    return NS_OK;
   }
   return nsBoxFrame::InsertFrames(aListName, aPrevFrame, aFrameList);
 }
 
 NS_IMETHODIMP
 nsPopupSetFrame::SetInitialChildList(nsIAtom*        aListName,
                                      nsFrameList&    aChildList)
 {
   if (aListName == nsGkAtoms::popupList) {
-    return AddPopupFrameList(aChildList);
+    // XXXmats this asserts because we don't implement
+    // GetChildList(nsGkAtoms::popupList) so nsCSSFrameConstructor
+    // believes it's empty and calls us multiple times.
+    //NS_ASSERTION(mPopupList.IsEmpty(),
+    //             "SetInitialChildList on non-empty child list");
+    AddPopupFrameList(aChildList);
+    return NS_OK;
   }
   return nsBoxFrame::SetInitialChildList(aListName, aChildList);
 }
 
 void
 nsPopupSetFrame::DestroyFrom(nsIFrame* aDestructRoot)
 {
-  // remove each popup from the list as we go.
-  while (mPopupList) {
-    nsPopupFrameList* temp = mPopupList;
-    mPopupList = mPopupList->mNextPopup;
-    temp->Destroy(aDestructRoot); // destroys frame
-  }
+  mPopupList.DestroyFramesFrom(aDestructRoot);
 
   // Normally the root box is our grandparent, but in case of wrapping
   // it can be our great-grandparent.
   nsIRootBox *rootBox = nsIRootBox::GetRootBox(PresContext()->GetPresShell());
   if (rootBox) {
     rootBox->SetPopupSetFrame(nsnull);
   }
 
@@ -166,20 +148,19 @@ nsPopupSetFrame::DestroyFrom(nsIFrame* a
 
 NS_IMETHODIMP
 nsPopupSetFrame::DoLayout(nsBoxLayoutState& aState)
 {
   // lay us out
   nsresult rv = nsBoxFrame::DoLayout(aState);
 
   // lay out all of our currently open popups.
-  nsPopupFrameList* currEntry = mPopupList;
-  while (currEntry) {
-    nsMenuPopupFrame* popupChild = currEntry->mPopupFrame;
-    if (popupChild && popupChild->IsOpen()) {
+  for (nsFrameList::Enumerator e(mPopupList); !e.AtEnd(); e.Next()) {
+    nsMenuPopupFrame* popupChild = static_cast<nsMenuPopupFrame*>(e.get());
+    if (popupChild->IsOpen()) {
       // then get its preferred size
       nsSize prefSize = popupChild->GetPrefSize(aState);
       nsSize minSize = popupChild->GetMinSize(aState);
       nsSize maxSize = popupChild->GetMaxSize(aState);
 
       prefSize = BoundsCheck(minSize, prefSize, maxSize);
 
       popupChild->SetPreferredBounds(aState, nsRect(0,0,prefSize.width, prefSize.height));
@@ -217,106 +198,42 @@ nsPopupSetFrame::DoLayout(nsBoxLayoutSta
           popupChild->GetRect().height > bounds.height) {
         // the size after layout was larger than the preferred size,
         // so set the preferred size accordingly
         popupChild->SetPreferredSize(popupChild->GetSize());
         popupChild->SetPopupPosition(nsnull, PR_FALSE);
       }
       popupChild->AdjustView();
     }
-
-    currEntry = currEntry->mNextPopup;
   }
 
   return rv;
 }
 
-nsresult
+void
 nsPopupSetFrame::RemovePopupFrame(nsIFrame* aPopup)
 {
-  // This was called by the Destroy() method of the popup, so all we have to do is
-  // get the popup out of our list, so we don't reflow it later.
-#ifdef DEBUG
-  PRBool found = PR_FALSE;
-#endif
-  nsPopupFrameList* currEntry = mPopupList;
-  nsPopupFrameList* temp = nsnull;
-  while (currEntry) {
-    if (currEntry->mPopupFrame == aPopup) {
-      // Remove this entry.
-      if (temp)
-        temp->mNextPopup = currEntry->mNextPopup;
-      else
-        mPopupList = currEntry->mNextPopup;
-      
-      NS_ASSERTION((aPopup->GetStateBits() & NS_FRAME_OUT_OF_FLOW) &&
-                   aPopup->GetType() == nsGkAtoms::menuPopupFrame,
-                   "found wrong type of frame in popupset's ::popupList");
-      // Delete the entry.
-      currEntry->mNextPopup = nsnull;
-      currEntry->Destroy(); // destroys the frame
-#ifdef DEBUG
-      found = PR_TRUE;
-#endif
+  NS_PRECONDITION((aPopup->GetStateBits() & NS_FRAME_OUT_OF_FLOW) &&
+                  aPopup->GetType() == nsGkAtoms::menuPopupFrame,
+                  "removing wrong type of frame in popupset's ::popupList");
 
-      // Break out of the loop.
-      break;
-    }
-
-    temp = currEntry;
-    currEntry = currEntry->mNextPopup;
-  }
-
-  NS_ASSERTION(found, "frame to remove is not in our ::popupList");
-  return NS_OK;
+  mPopupList.DestroyFrame(aPopup);
 }
 
-nsresult
+void
 nsPopupSetFrame::AddPopupFrameList(nsFrameList& aPopupFrameList)
 {
-  while (!aPopupFrameList.IsEmpty()) {
-    nsIFrame* f = aPopupFrameList.FirstChild();
-    // Clears out prev/next sibling points appropriately. Every frame
-    // in our popup list has null next and prev pointers, they're logically
-    // each in their own list.
-    aPopupFrameList.RemoveFrame(f);
-    nsresult rv = AddPopupFrame(f);
-    NS_ENSURE_SUCCESS(rv, rv);
+#ifdef DEBUG
+  for (nsFrameList::Enumerator e(aPopupFrameList); !e.AtEnd(); e.Next()) {
+    NS_ASSERTION((e.get()->GetStateBits() & NS_FRAME_OUT_OF_FLOW) &&
+                 e.get()->GetType() == nsGkAtoms::menuPopupFrame,
+                 "adding wrong type of frame in popupset's ::popupList");
   }
-  return NS_OK;
-}
-
-nsresult
-nsPopupSetFrame::AddPopupFrame(nsIFrame* aPopup)
-{
-  NS_ASSERTION((aPopup->GetStateBits() & NS_FRAME_OUT_OF_FLOW) &&
-               aPopup->GetType() == nsGkAtoms::menuPopupFrame,
-               "adding wrong type of frame in popupset's ::popupList");
-
-  // The entry should already exist, but might not (if someone decided to make their
-  // popup visible straightaway, e.g., the autocomplete widget).
-  // First look for an entry by content.
-  nsIContent* content = aPopup->GetContent();
-  nsPopupFrameList* entry = mPopupList;
-  while (entry && entry->mPopupContent != content)
-    entry = entry->mNextPopup;
-  if (!entry) {
-    entry = new nsPopupFrameList(content, mPopupList);
-    if (!entry)
-      return NS_ERROR_OUT_OF_MEMORY;
-    mPopupList = entry;
-  }
-  else {
-    NS_ASSERTION(!entry->mPopupFrame, "Leaking a popup frame");
-  }
-
-  // Set the frame connection.
-  entry->mPopupFrame = static_cast<nsMenuPopupFrame *>(aPopup);
-  
-  return NS_OK;
+#endif
+  mPopupList.InsertFrames(nsnull, nsnull, aPopupFrameList);
 }
 
 #ifdef DEBUG
 NS_IMETHODIMP
 nsPopupSetFrame::List(FILE* out, PRInt32 aIndent) const
 {
   IndentBy(out, aIndent);
   ListTag(out);
@@ -384,29 +301,29 @@ nsPopupSetFrame::List(FILE* out, PRInt32
       fputs(">\n", out);
     }
     listName = GetAdditionalChildListName(listIndex++);
   } while(nsnull != listName);
 
   // XXXmats the above is copy-pasted from nsContainerFrame::List which is lame,
   // clean this up after bug 399111 is implemented.
 
-  if (mPopupList) {
+  if (!mPopupList.IsEmpty()) {
     fputs("<\n", out);
     ++aIndent;
     IndentBy(out, aIndent);
     nsAutoString tmp;
     nsGkAtoms::popupList->ToString(tmp);
     fputs(NS_LossyConvertUTF16toASCII(tmp).get(), out);
     fputs(" for ", out);
     ListTag(out);
     fputs(" <\n", out);
     ++aIndent;
-    for (nsPopupFrameList* l = mPopupList; l; l = l->mNextPopup) {
-      l->mPopupFrame->List(out, aIndent);
+    for (nsFrameList::Enumerator e(mPopupList); !e.AtEnd(); e.Next()) {
+      e.get()->List(out, aIndent);
     }
     --aIndent;
     IndentBy(out, aIndent);
     fputs(">\n", out);
     --aIndent;
     IndentBy(out, aIndent);
     fputs(">\n", out);
     outputOneList = PR_TRUE;
--- a/layout/xul/base/src/nsPopupSetFrame.h
+++ b/layout/xul/base/src/nsPopupSetFrame.h
@@ -31,42 +31,24 @@
  * use your version of this file under the terms of the MPL, indicate your
  * decision by deleting the provisions above and replace them with the notice
  * and other provisions required by the GPL or the LGPL. If you do not delete
  * the provisions above, a recipient may use your version of this file under
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 
-//
-// nsPopupSetFrame
-//
-
 #ifndef nsPopupSetFrame_h__
 #define nsPopupSetFrame_h__
 
 #include "nsIAtom.h"
-
 #include "nsBoxFrame.h"
-#include "nsMenuPopupFrame.h"
-
-class nsCSSFrameConstructor;
 
 nsIFrame* NS_NewPopupSetFrame(nsIPresShell* aPresShell, nsStyleContext* aContext);
 
-struct nsPopupFrameList {
-  nsPopupFrameList* mNextPopup;  // The next popup in the list.
-  nsMenuPopupFrame* mPopupFrame; // Our popup.
-  nsIContent* mPopupContent;     // The content element for the <popup> itself.
-
-public:
-  nsPopupFrameList(nsIContent* aPopupContent, nsPopupFrameList* aNext);
-  void Destroy(nsIFrame* aDestructRoot = nsnull);
-};
-
 class nsPopupSetFrame : public nsBoxFrame
 {
 public:
   NS_DECL_FRAMEARENA_HELPERS
 
   nsPopupSetFrame(nsIPresShell* aShell, nsStyleContext* aContext):
     nsBoxFrame(aShell, aContext) {}
 
@@ -80,35 +62,32 @@ public:
   NS_IMETHOD RemoveFrame(nsIAtom*        aListName,
                          nsIFrame*       aOldFrame);
   NS_IMETHOD InsertFrames(nsIAtom*        aListName,
                           nsIFrame*       aPrevFrame,
                           nsFrameList&    aFrameList);
   NS_IMETHOD  SetInitialChildList(nsIAtom*        aListName,
                                   nsFrameList&    aChildList);
 
-    // nsIBox
+  // nsIBox
   NS_IMETHOD DoLayout(nsBoxLayoutState& aBoxLayoutState);
 
   // Used to destroy our popup frames.
   virtual void DestroyFrom(nsIFrame* aDestructRoot);
 
   virtual nsIAtom* GetType() const;
 
 #ifdef DEBUG
   NS_IMETHOD List(FILE* out, PRInt32 aIndent) const;
   NS_IMETHOD GetFrameName(nsAString& aResult) const
   {
       return MakeFrameName(NS_LITERAL_STRING("PopupSet"), aResult);
   }
 #endif
 
 protected:
-
-  nsresult AddPopupFrameList(nsFrameList& aPopupFrameList);
-  nsresult AddPopupFrame(nsIFrame* aPopup);
-  nsresult RemovePopupFrame(nsIFrame* aPopup);
+  void AddPopupFrameList(nsFrameList& aPopupFrameList);
+  void RemovePopupFrame(nsIFrame* aPopup);
   
-  nsPopupFrameList* mPopupList;
-
-}; // class nsPopupSetFrame
+  nsFrameList mPopupList;
+};
 
 #endif
--- a/media/liboggz/README_MOZILLA
+++ b/media/liboggz/README_MOZILLA
@@ -30,8 +30,10 @@ bug504843.patch: Propogate read errors f
 bug519155.patch: Fix oggz seek's reset so that it can rollback on fail correctly.
 
 bug498380.patch: Remove bogus assert.
 
 bug520493.patch: Fix oggz seek so that it doesn't exit too early, and to use
                  more accurate page offsets while bisecting.
 
 bug523335.patch: Abort oggz seek bisection when the underlying stream closes.
+
+bug533822.patch: Clear packets queued for granulepos calcuation when resetting streams.
new file mode 100644
--- /dev/null
+++ b/media/liboggz/bug533822.patch
@@ -0,0 +1,21 @@
+diff --git a/media/liboggz/src/liboggz/oggz_seek.c b/media/liboggz/src/liboggz/oggz_seek.c
+--- a/media/liboggz/src/liboggz/oggz_seek.c
++++ b/media/liboggz/src/liboggz/oggz_seek.c
+@@ -135,16 +135,17 @@ oggz_stream_reset (void * data)
+   }
+ 
+   return 0;
+ }
+ 
+ static void
+ oggz_reset_streams (OGGZ * oggz)
+ {
++  oggz_dlist_deliter(oggz->packet_buffer, oggz_read_free_pbuffers);
+   oggz_vector_foreach (oggz->streams, oggz_stream_reset);
+ }
+ 
+ static long
+ oggz_reset_seek (OGGZ * oggz, oggz_off_t offset, ogg_int64_t unit, int whence)
+ {
+   OggzReader * reader = &oggz->x.reader;
+ 
--- a/media/liboggz/src/liboggz/oggz_seek.c
+++ b/media/liboggz/src/liboggz/oggz_seek.c
@@ -135,16 +135,17 @@ oggz_stream_reset (void * data)
   }
 
   return 0;
 }
 
 static void
 oggz_reset_streams (OGGZ * oggz)
 {
+  oggz_dlist_deliter(oggz->packet_buffer, oggz_read_free_pbuffers);
   oggz_vector_foreach (oggz->streams, oggz_stream_reset);
 }
 
 static long
 oggz_reset_seek (OGGZ * oggz, oggz_off_t offset, ogg_int64_t unit, int whence)
 {
   OggzReader * reader = &oggz->x.reader;
 
--- a/media/liboggz/update.sh
+++ b/media/liboggz/update.sh
@@ -58,9 +58,9 @@ patch -p3 <bug496063.patch
 patch -p3 <faster_seek.patch
 patch -p3 <bug516847.patch
 patch -p3 <bug518169.patch
 patch -p3 <bug504843.patch
 patch -p3 <bug519155.patch
 patch -p3 <bug498380.patch
 patch -p3 <bug520493.patch
 patch -p3 <bug523335.patch
-
+patch -p3 <bug533822.patch
--- a/media/libsydneyaudio/README_MOZILLA
+++ b/media/libsydneyaudio/README_MOZILLA
@@ -18,8 +18,10 @@ sydney_os2_base.patch: Bug 448918 - add 
 
 sydney_os2_moz.patch:  Bug 448918 - add Mozilla-specific code to
                        sydney_audio_os2.c
 
 bug495794_closeAudio.patch fixes a crash when destroying the sa_stream_t after
 a failed attempt to open the stream.
 
 bug495558_alsa_endian.patch adds support for big endian ALSA platforms.
+
+bug526411_latency.patch: reduce requested latency to 250ms to match OGGPLAY_AUDIO_OFFSET.
new file mode 100644
--- /dev/null
+++ b/media/libsydneyaudio/bug526411_latency.patch
@@ -0,0 +1,22 @@
+diff --git a/media/libsydneyaudio/src/sydney_audio_alsa.c b/media/libsydneyaudio/src/sydney_audio_alsa.c
+--- a/media/libsydneyaudio/src/sydney_audio_alsa.c
++++ b/media/libsydneyaudio/src/sydney_audio_alsa.c
+@@ -138,17 +138,17 @@ sa_stream_open(sa_stream_t *s) {
+                          SND_PCM_FORMAT_S16_LE,
+ #else
+                          SND_PCM_FORMAT_S16_BE,
+ #endif
+                          SND_PCM_ACCESS_RW_INTERLEAVED,
+                          s->n_channels,
+                          s->rate,
+                          1,
+-                         500000) < 0) {
++                         250000) < 0) {
+     snd_pcm_close(s->output_unit);
+     s->output_unit = NULL;
+     return SA_ERROR_NOT_SUPPORTED;
+   }
+   
+   return SA_SUCCESS;
+ }
+ 
--- a/media/libsydneyaudio/src/sydney_audio_alsa.c
+++ b/media/libsydneyaudio/src/sydney_audio_alsa.c
@@ -138,17 +138,17 @@ sa_stream_open(sa_stream_t *s) {
                          SND_PCM_FORMAT_S16_LE,
 #else
                          SND_PCM_FORMAT_S16_BE,
 #endif
                          SND_PCM_ACCESS_RW_INTERLEAVED,
                          s->n_channels,
                          s->rate,
                          1,
-                         500000) < 0) {
+                         250000) < 0) {
     snd_pcm_close(s->output_unit);
     s->output_unit = NULL;
     return SA_ERROR_NOT_SUPPORTED;
   }
   
   return SA_SUCCESS;
 }
 
--- a/media/libsydneyaudio/update.sh
+++ b/media/libsydneyaudio/update.sh
@@ -6,8 +6,9 @@ cp $1/include/sydney_audio.h include/syd
 cp $1/src/*.c src/
 cp $1/AUTHORS ./AUTHORS
 patch -p4 <pause-resume.patch
 patch -p4 <include-CoreServices.patch
 patch -p4 <sydney_os2_base.patch
 patch -p4 <sydney_os2_moz.patch
 patch -p3 <bug495794_closeAudio.patch
 patch -p3 < bug495558_alsa_endian.patch
+patch -p3 <bug526411_latency.patch
--- a/modules/plugin/Makefile.in
+++ b/modules/plugin/Makefile.in
@@ -63,19 +63,21 @@ endif
 ifeq ($(OS_ARCH),WINNT)
 TOOL_DIRS += default/windows
 endif
 
 ifeq ($(OS_ARCH),OS2)
 TOOL_DIRS += default/os2
 endif
 
+ifdef PBBUILD_BIN
 ifeq ($(MOZ_WIDGET_TOOLKIT),cocoa)
 TOOL_DIRS += default/mac
 endif
+endif
 
 ifdef ENABLE_TESTS
 ifneq (,$(filter WINNT Darwin Linux OS2 SunOS,$(OS_ARCH)))
 DIRS += test
 TOOL_DIRS += sdk
 endif
 endif
 
--- a/modules/plugin/base/public/npapi.h
+++ b/modules/plugin/base/public/npapi.h
@@ -333,17 +333,17 @@ typedef enum {
 
 #ifdef XP_MACOSX
   /* Used for negotiating drawing models */
   , NPPVpluginDrawingModel = 1000
   /* Used for negotiating event models */
   , NPPVpluginEventModel = 1001
 #endif
 
-#ifdef MOZ_PLATFORM_HILDON
+#if (MOZ_PLATFORM_MAEMO == 5)
   , NPPVpluginWindowlessLocalBool = 2002
 #endif
 } NPPVariable;
 
 /*
  * List of variable names for which NPN_GetValue is implemented by Mozilla
  */
 typedef enum {
@@ -378,17 +378,17 @@ typedef enum {
   , NPNVsupportsQuickDrawBool = 2000
 #endif
   , NPNVsupportsCoreGraphicsBool = 2001
 #ifndef NP_NO_CARBON
   , NPNVsupportsCarbonBool = 3000 /* TRUE if the browser supports the Carbon event model */
 #endif
   , NPNVsupportsCocoaBool = 3001 /* TRUE if the browser supports the Cocoa event model */
 #endif
-#ifdef MOZ_PLATFORM_HILDON
+#if (MOZ_PLATFORM_MAEMO == 5)
   , NPNVSupportsWindowlessLocal = 2002
 #endif
 } NPNVariable;
 
 typedef enum {
   NPNURLVCookie = 501,
   NPNURLVProxy
 } NPNURLVariable;
--- a/modules/plugin/base/public/nsPluginNativeWindow.h
+++ b/modules/plugin/base/public/nsPluginNativeWindow.h
@@ -98,17 +98,17 @@ public:
     if (aPluginInstance)
       aPluginInstance->SetWindow(this);
     else if (mPluginInstance)
       mPluginInstance->SetWindow(nsnull);
 
     SetPluginInstance(aPluginInstance);
     return NS_OK;
   }
-#if defined(MOZ_PLATFORM_HILDON) && defined(MOZ_WIDGET_GTK2)
+#if (MOZ_PLATFORM_MAEMO == 5)
 #define MOZ_COMPOSITED_PLUGINS
 #endif
 #ifdef MOZ_COMPOSITED_PLUGINS
   /* XXX: we use this to leak the socket widget out from nsPlugNativeWindowGtk2
      so that Renderer::NativeDraw() in nsObjectFrame.cpp can draw the widget.
      I don't currently know a better way to do this... */
   void *mPlugWindow;
 #endif
--- a/modules/plugin/base/src/nsNPAPIPlugin.cpp
+++ b/modules/plugin/base/src/nsNPAPIPlugin.cpp
@@ -295,20 +295,20 @@ void
 nsNPAPIPlugin::SetPluginRefNum(short aRefNum)
 {
   mPluginRefNum = aRefNum;
 }
 #endif
 
 #ifdef MOZ_IPC
 void
-nsNPAPIPlugin::PluginCrashed()
+nsNPAPIPlugin::PluginCrashed(const nsAString& dumpID)
 {
   nsRefPtr<nsPluginHost> host = dont_AddRef(nsPluginHost::GetInst());
-  host->PluginCrashed(this);
+  host->PluginCrashed(this, dumpID);
 }
 #endif
 
 namespace {
 
 #ifdef MOZ_IPC
 
 inline PRBool
@@ -2012,17 +2012,21 @@ NPError NP_CALLBACK
       nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *) npp->ndata;
       PRBool windowless = PR_FALSE;
       inst->IsWindowless(&windowless);
       NPBool needXEmbed = PR_FALSE;
       if (!windowless) {
         inst->GetValueFromPlugin(NPPVpluginNeedsXEmbed, &needXEmbed);
       }
       if (windowless || needXEmbed) {
+#ifdef MOZ_WIDGET_GTK2
         (*(Display **)result) = GDK_DISPLAY();
+#else
+        (*(Display **)result) = QX11Info::display();
+#endif
         return NPERR_NO_ERROR;
       }
     }
     // adobe nppdf calls XtGetApplicationNameAndClass(display,
     // &instance, &class) we have to init Xt toolkit before get
     // XtDisplay just call gtk_xtbin_new(w,0) once
     static GtkWidget *gtkXtBinHolder = 0;
     if (!gtkXtBinHolder) {
@@ -2134,17 +2138,17 @@ NPError NP_CALLBACK
       PRBool enabled;
       pbs->GetPrivateBrowsingEnabled(&enabled);
       *(NPBool*)result = (NPBool)enabled;
       return NPERR_NO_ERROR;
     }
     return NPERR_GENERIC_ERROR;
   }
 
-#ifdef MOZ_PLATFORM_HILDON
+#if (MOZ_PLATFORM_MAEMO == 5)
   case NPNVSupportsWindowlessLocal: {
     *(NPBool*)result = PR_TRUE;
     return NPERR_NO_ERROR;
   }
 #endif
 
 #ifdef XP_MACOSX
   case NPNVpluginDrawingModel: {
@@ -2272,17 +2276,17 @@ NPError NP_CALLBACK
       // NPERR_NO_ERROR here to conform to other browsers' behavior on OS X
       // (e.g. Safari and Opera).
       return NPERR_NO_ERROR;
 #else
       NPBool bWindowless = (result == nsnull);
       return inst->SetWindowless(bWindowless);
 #endif
     }
-#ifdef MOZ_PLATFORM_HILDON
+#if (MOZ_PLATFORM_MAEMO == 5)
     case NPPVpluginWindowlessLocalBool: {
       NPBool bWindowlessLocal = (result != nsnull);
       return inst->SetWindowlessLocal(bWindowlessLocal);
     }
 #endif
     case NPPVpluginTransparentBool: {
       NPBool bTransparent = (result != nsnull);
       return inst->SetTransparent(bTransparent);
--- a/modules/plugin/base/src/nsNPAPIPlugin.h
+++ b/modules/plugin/base/src/nsNPAPIPlugin.h
@@ -88,18 +88,19 @@ public:
   static nsresult CreatePlugin(const char* aFilePath, PRLibrary* aLibrary,
                                nsIPlugin** aResult);
 #ifdef XP_MACOSX
   void SetPluginRefNum(short aRefNum);
 #endif
 
 #ifdef MOZ_IPC
   // The IPC mechanism notifies the nsNPAPIPlugin if the plugin crashes and is
-  // no longer usable.
-  void PluginCrashed();
+  // no longer usable. dumpID is the ID of a minidump that was written,
+  // or empty if no minidump was written.
+  void PluginCrashed(const nsAString& dumpID);
 #endif
 
 protected:
   // Ensures that the static browser functions are properly initialized
   static void CheckClassInitialized();
 
 #ifdef XP_MACOSX
   short mPluginRefNum;
--- a/modules/plugin/base/src/nsNPAPIPluginInstance.cpp
+++ b/modules/plugin/base/src/nsNPAPIPluginInstance.cpp
@@ -1387,17 +1387,17 @@ NS_IMETHODIMP nsNPAPIPluginInstance::Han
     mCurrentPluginEvent = nsnull;
   }
 
   return NS_OK;
 }
 
 NS_IMETHODIMP nsNPAPIPluginInstance::GetValueFromPlugin(NPPVariable variable, void* value)
 {
-#ifdef MOZ_PLATFORM_HILDON
+#if (MOZ_PLATFORM_MAEMO == 5)
   // The maemo flash plugin does not remember this.  It sets the
   // value, but doesn't support the get value.
   if (variable == NPPVpluginWindowlessLocalBool) {
     *(NPBool*)value = mWindowlessLocal;
     return NS_OK;
   }
 #endif
   nsresult  res = NS_OK;
--- a/modules/plugin/base/src/nsPluginHost.cpp
+++ b/modules/plugin/base/src/nsPluginHost.cpp
@@ -84,16 +84,17 @@
 #include "nsPluginLogging.h"
 #include "nsIPrefBranch2.h"
 #include "nsIScriptChannel.h"
 #include "nsPrintfCString.h"
 #include "nsIBlocklistService.h"
 #include "nsVersionComparator.h"
 #include "nsIPrivateBrowsingService.h"
 #include "nsIObjectLoadingContent.h"
+#include "nsIWritablePropertyBag2.h"
 
 #include "nsEnumeratorUtils.h"
 #include "nsXPCOM.h"
 #include "nsXPCOMCID.h"
 #include "nsISupportsPrimitives.h"
 
 // for the dialog
 #include "nsIStringBundle.h"
@@ -5202,35 +5203,47 @@ NS_IMETHODIMP nsPluginHost::Notify(nsITi
     return NS_OK;
   }
 #endif
   return NS_ERROR_FAILURE;
 }
 
 #ifdef MOZ_IPC
 void
-nsPluginHost::PluginCrashed(nsNPAPIPlugin* aPlugin)
+nsPluginHost::PluginCrashed(nsNPAPIPlugin* aPlugin, const nsAString& dumpID)
 {
   nsPluginTag* pluginTag = FindTagForPlugin(aPlugin);
   if (!pluginTag) {
     NS_WARNING("nsPluginTag not found in nsPluginHost::PluginCrashed");
     return;
   }
 
+  // Notify the app's observer that a plugin crashed so it can submit a crashreport.
+  PRBool submittedCrashReport = PR_FALSE;
+  nsCOMPtr<nsIObserverService> obsService = do_GetService("@mozilla.org/observer-service;1");
+  nsCOMPtr<nsIWritablePropertyBag2> propbag = do_CreateInstance("@mozilla.org/hash-property-bag;1");
+  if (obsService && propbag) {
+    propbag->SetPropertyAsAString(NS_LITERAL_STRING("minidumpID"), dumpID);
+    obsService->NotifyObservers(propbag, "plugin-crashed", nsnull);
+    // see if an observer submitted a crash report.
+    propbag->GetPropertyAsBool(NS_LITERAL_STRING("submittedCrashReport"), &submittedCrashReport);
+  }
+
   // Invalidate each nsPluginInstanceTag for the crashed plugin
 
   for (PRUint32 i = mInstanceTags.Length(); i > 0; i--) {
     nsPluginInstanceTag* instanceTag = mInstanceTags[i - 1];
     if (instanceTag->mPluginTag == pluginTag) {
       // notify the content node (nsIObjectLoadingContent) that the plugin has crashed
       nsCOMPtr<nsIDOMElement> domElement;
       instanceTag->mInstance->GetDOMElement(getter_AddRefs(domElement));
       nsCOMPtr<nsIObjectLoadingContent> objectContent(do_QueryInterface(domElement));
       if (objectContent) {
-        objectContent->PluginCrashed();
+        objectContent->PluginCrashed(NS_ConvertUTF8toUTF16(pluginTag->mName),
+                                     submittedCrashReport);
       }
       
       instanceTag->mInstance->Stop();
 
       nsPluginTag* pluginTag = instanceTag->mPluginTag;
       mInstanceTags.RemoveElement(instanceTag);
       OnPluginInstanceDestroyed(pluginTag);
     }
@@ -5338,17 +5351,17 @@ nsresult nsPluginStreamListenerPeer::Ser
   // mInstance->Stop calls mPStreamListener->CleanUpStream(), so stream will be properly clean up
   mInstance->Stop();
   mInstance->Start();
   nsCOMPtr<nsIPluginInstanceOwner> owner;
   mInstance->GetOwner(getter_AddRefs(owner));
   if (owner) {
     NPWindow* window = nsnull;
     owner->GetWindow(window);
-#if defined (MOZ_WIDGET_GTK2)
+#if defined(MOZ_WIDGET_GTK2) || defined(MOZ_WIDGET_QT)
     // Should call GetPluginPort() here.
     // This part is copied from nsPluginInstanceOwner::GetPluginPort(). 
     nsCOMPtr<nsIWidget> widget;
     ((nsPluginNativeWindow*)window)->GetPluginWidget(getter_AddRefs(widget));
     if (widget) {
       window->window = widget->GetNativeData(NS_NATIVE_PLUGIN_PORT);
     }
 #endif
--- a/modules/plugin/base/src/nsPluginHost.h
+++ b/modules/plugin/base/src/nsPluginHost.h
@@ -155,17 +155,17 @@ public:
   static nsresult GetPrompt(nsIPluginInstanceOwner *aOwner, nsIPrompt **aPrompt);
 
   static nsresult PostPluginUnloadEvent(PRLibrary* aLibrary);
 
   void AddIdleTimeTarget(nsIPluginInstanceOwner* objectFrame, PRBool isVisible);
   void RemoveIdleTimeTarget(nsIPluginInstanceOwner* objectFrame);
 
 #ifdef MOZ_IPC
-  void PluginCrashed(nsNPAPIPlugin* plugin);
+  void PluginCrashed(nsNPAPIPlugin* plugin, const nsAString& dumpID);
 #endif
 
   nsPluginInstanceTag *FindInstanceTag(nsIPluginInstance *instance);
   nsPluginInstanceTag *FindInstanceTag(const char *mimetype);
   nsPluginInstanceTag *FindStoppedInstanceTag(const char * url);
   nsPluginInstanceTag *FindOldestStoppedInstanceTag();
   PRUint32 StoppedInstanceTagCount();
 
--- a/modules/plugin/base/src/nsPluginNativeWindowGtk2.cpp
+++ b/modules/plugin/base/src/nsPluginNativeWindowGtk2.cpp
@@ -44,17 +44,17 @@
 
 #include "nsDebug.h"
 #include "nsPluginNativeWindow.h"
 #include "npapi.h"
 #include <gtk/gtk.h>
 #include <gdk/gdkx.h>
 #include <gdk/gdk.h>
 
-#ifdef MOZ_PLATFORM_HILDON
+#if (MOZ_PLATFORM_MAEMO == 5)
 #define MOZ_COMPOSITED_PLUGINS
 #endif
 
 #ifdef MOZ_COMPOSITED_PLUGINS
 extern "C" {
 #include <X11/extensions/Xdamage.h>
 #include <X11/extensions/Xcomposite.h>
 }
--- a/modules/plugin/base/src/nsPluginsDirDarwin.cpp
+++ b/modules/plugin/base/src/nsPluginsDirDarwin.cpp
@@ -215,38 +215,54 @@ static void ParsePlistPluginInfo(nsPlugi
 
 nsPluginFile::nsPluginFile(nsIFile *spec)
     : mPlugin(spec)
 {
 }
 
 nsPluginFile::~nsPluginFile() {}
 
-/**
- * Loads the plugin into memory using NSPR's shared-library loading
- * mechanism. Handles platform differences in loading shared libraries.
- */
 nsresult nsPluginFile::LoadPlugin(PRLibrary* &outLibrary)
 {
-  const char* path;
-
   if (!mPlugin)
     return NS_ERROR_NULL_POINTER;
 
-  nsCAutoString temp;
-  mPlugin->GetNativePath(temp);
-  path = temp.get();
+  char executablePath[PATH_MAX];
+  executablePath[0] = '\0';
 
-  outLibrary = PR_LoadLibrary(path);
+  // We store the path to the plugin bundle, we need the executable path here.
+  // 64-bit NSPR does not support bundles.
+  nsCAutoString bundlePath;
+  mPlugin->GetNativePath(bundlePath);
+  CFStringRef pathRef = ::CFStringCreateWithCString(NULL, bundlePath.get(), kCFStringEncodingUTF8);
+  if (pathRef) {
+    CFURLRef bundleURL = ::CFURLCreateWithFileSystemPath(NULL, pathRef, kCFURLPOSIXPathStyle, true);
+    if (bundleURL) {
+      CFBundleRef bundle = ::CFBundleCreate(NULL, bundleURL);
+      if (bundle) {
+        CFURLRef executableURL = ::CFBundleCopyExecutableURL(bundle);
+        if (executableURL) {
+          if (!::CFURLGetFileSystemRepresentation(executableURL, true, (UInt8*)&executablePath, PATH_MAX))
+            executablePath[0] = '\0';
+          ::CFRelease(executableURL);
+        }
+        ::CFRelease(bundle);
+      }
+      ::CFRelease(bundleURL);
+    }
+    ::CFRelease(pathRef); 
+  }
+
+  outLibrary = PR_LoadLibrary(executablePath);
   pLibrary = outLibrary;
   if (!outLibrary) {
     return NS_ERROR_FAILURE;
   }
 #ifdef DEBUG
-  printf("[loaded plugin %s]\n", path);
+  printf("[loaded plugin %s]\n", bundlePath.get());
 #endif
   return NS_OK;
 }
 
 static char* p2cstrdup(StringPtr pstr)
 {
   int len = pstr[0];
   char* cstr = static_cast<char*>(NS_Alloc(len + 1));
--- a/modules/plugin/test/mochitest/Makefile.in
+++ b/modules/plugin/test/mochitest/Makefile.in
@@ -40,77 +40,78 @@ topsrcdir	= @top_srcdir@
 srcdir		= @srcdir@
 VPATH		= @srcdir@
 relativesrcdir  = modules/plugin/test
 
 include $(DEPTH)/config/autoconf.mk
 include $(topsrcdir)/config/rules.mk
 
 _MOCHITEST_FILES = \
-		test_getauthenticationinfo.html \
-		test_npobject_getters.html \
-		test_npruntime_npnevaluate.html \
-		test_npruntime_npninvoke.html \
-		test_npruntime_npninvokedefault.html \
-		loremipsum.txt \
-		loremipsum_file.txt \
-		post.sjs \
-		pluginstream.js \
-		plugin_window.html \
-		test_painting.html \
-		test_pluginstream_err.html \
-		test_pluginstream_src.html \
-		test_pluginstream_geturl.html \
-		test_pluginstream_geturlnotify.html \
-		test_pluginstream_asfile.html \
-		test_pluginstream_asfileonly.html \
-		test_pluginstream_post.html \
-		test_pluginstream_poststream.html \
-		test_pluginstream_seek.html \
-		test_pluginstream_newstream.html \
-		test_multipleinstanceobjects.html \
-		test_streamNotify.html \
-		test_instantiation.html \
-		test_cookies.html \
-		test_npn_timers.html \
-		test_npn_asynccall.html \
-		$(NULL)
+  test_getauthenticationinfo.html \
+  test_npobject_getters.html \
+  test_npruntime_npnevaluate.html \
+  test_npruntime_npninvoke.html \
+  test_npruntime_npninvokedefault.html \
+  loremipsum.txt \
+  loremipsum_file.txt \
+  post.sjs \
+  pluginstream.js \
+  plugin_window.html \
+  test_painting.html \
+  test_pluginstream_err.html \
+  test_pluginstream_src.html \
+  test_pluginstream_geturl.html \
+  test_pluginstream_geturlnotify.html \
+  test_pluginstream_asfile.html \
+  test_pluginstream_asfileonly.html \
+  test_pluginstream_post.html \
+  test_pluginstream_poststream.html \
+  test_pluginstream_seek.html \
+  test_pluginstream_newstream.html \
+  test_multipleinstanceobjects.html \
+  test_streamNotify.html \
+  test_instantiation.html \
+  test_cookies.html \
+  test_npn_timers.html \
+  test_npn_asynccall.html \
+  $(NULL)
 
-#		test_npruntime_npnsetexception.html \ Disabled for e10s
+#  test_npruntime_npnsetexception.html \ Disabled for e10s
 
 ifdef MOZ_IPC
 _MOCHITEST_FILES += \
-		test_crashing.html \
-		test_crashing2.html \
-		crashing_subpage.html \
-		$(NULL)
+  test_crashing.html \
+  test_crashing2.html \
+  crashing_subpage.html \
+  $(NULL)
 endif
 
 ifeq ($(OS_ARCH),WINNT)
 _MOCHITEST_FILES += \
- 		test_windowed_invalidate.html \
-        $(NULL)
+  test_windowed_invalidate.html \
+  $(NULL)
 endif
 
 _MOCHICHROME_FILES = \
-		test_bug479979.xul \
-		test_npruntime.xul   \
-		test_privatemode.xul \
-		test_wmode.xul \
-		$(NULL)
+  test_bug479979.xul \
+  test_npruntime.xul   \
+  test_privatemode.xul \
+  test_wmode.xul \
+  $(NULL)
 
 ifeq (cocoa,$(MOZ_WIDGET_TOOLKIT))
 _MOCHICHROME_FILES += \
-		test_convertpoint.xul \
-		$(NULL)
+  test_convertpoint.xul \
+  $(NULL)
 endif
 
 ifdef MOZ_IPC
 _MOCHICHROME_FILES += \
-		test_crash_notify.xul \
-		$(NULL)
+  test_crash_notify.xul \
+  test_crash_notify_no_report.xul \
+  $(NULL)
 endif
 
 libs:: $(_MOCHICHROME_FILES)
 	$(INSTALL) $^ $(DEPTH)/_tests/testing/mochitest/chrome/$(relativesrcdir)
 
 libs:: $(_MOCHITEST_FILES)
 	$(INSTALL) $^ $(DEPTH)/_tests/testing/mochitest/tests/$(relativesrcdir)
--- a/modules/plugin/test/mochitest/test_crash_notify.xul
+++ b/modules/plugin/test/mochitest/test_crash_notify.xul
@@ -14,35 +14,98 @@
 <embed id="plugin1" type="application/x-test" width="200" height="200"></embed>
 </body>
 <script class="testbody" type="application/javascript">
 <![CDATA[
 SimpleTest.waitForExplicitFinish();
 
 var success = false;
 
+var observerFired = false;
+
+var testObserver = {
+  observe: function(subject, topic, data) {
+    observerFired = true;
+    ok(true, "Observer fired");
+    netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect');
+    is(topic, "plugin-crashed", "Checking correct topic");
+    is(data,  null, "Checking null data");
+    ok((subject instanceof Components.interfaces.nsIPropertyBag2), "got Propbag");
+    ok((subject instanceof Components.interfaces.nsIWritablePropertyBag2),
+"got writable Propbag");
+
+    var id = subject.getPropertyAsAString("minidumpID");
+    isnot(id, "", "got a non-empty crash id");
+    let directoryService =
+      Components.classes["@mozilla.org/file/directory_service;1"].
+      getService(Components.interfaces.nsIProperties);
+    let profD = directoryService.get("ProfD", Components.interfaces.nsIFile);
+    profD.append("minidumps");
+    let dumpFile = profD.clone();
+    dumpFile.append(id + ".dmp");
+    ok(dumpFile.exists(), "minidump exists");
+    let extraFile = profD.clone();
+    extraFile.append(id + ".extra");
+    ok(extraFile.exists(), "extra file exists");
+    // cleanup, to be nice
+    dumpFile.remove(false);
+    extraFile.remove(false);
+  },
+
+  QueryInterface: function(iid) {
+    netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect');
+    if (iid.equals(Components.interfaces.nsIObserver) ||
+        iid.equals(Components.interfaces.nsISupportsWeakReference) ||
+        iid.equals(Components.interfaces.nsISupports))
+      return this;
+    throw Components.results.NS_NOINTERFACE;
+  }
+};
+
+
 function onPluginCrashed(aEvent) {
   ok(true, "Plugin crashed notification received");
+  ok(observerFired, "Observer should have fired first");
+  is(aEvent.type, "PluginCrashed", "event is correct type");
 
   var pluginElement = document.getElementById("plugin1");
   is (pluginElement, aEvent.target, "Plugin crashed event target is plugin element");
 
+  netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect');
+  
+  ok(aEvent instanceof Components.interfaces.nsIDOMDataContainerEvent,
+     "plugin crashed event has the right interface");
+  var pluginName = aEvent.getData("pluginName");
+  is(pluginName, "Test Plug-in");
+  var didReport = aEvent.getData("submittedCrashReport");
+  // The app itself may or may not have decided to submit the report, so
+  // allow either true or false here.
+  ok((didReport == true || didReport == false), "event said crash report was submitted");
+
+  var os = Components.classes["@mozilla.org/observer-service;1"].
+           getService(Components.interfaces.nsIObserverService);
+  os.removeObserver(testObserver, "plugin-crashed");
+
   SimpleTest.finish();
 }
 
 function runTests() {
   netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect');
   var prefs = Components.classes['@mozilla.org/preferences-service;1']
     .getService(Components.interfaces.nsIPrefBranch);
   if (!prefs.getBoolPref('dom.ipc.plugins.enabled')) {
     ok(true, "Skipping this test when IPC plugins are not enabled.");
     SimpleTest.finish();
     return;
   }
 
+  var os = Components.classes["@mozilla.org/observer-service;1"].
+           getService(Components.interfaces.nsIObserverService);
+  os.addObserver(testObserver, "plugin-crashed", true);
+  
   document.addEventListener("PluginCrashed", onPluginCrashed, false);
 
   var pluginElement = document.getElementById("plugin1");
   try {
     pluginElement.crash();
   } catch (e) {
   }
 }
copy from modules/plugin/test/mochitest/test_crash_notify.xul
copy to modules/plugin/test/mochitest/test_crash_notify_no_report.xul
--- a/modules/plugin/test/mochitest/test_crash_notify.xul
+++ b/modules/plugin/test/mochitest/test_crash_notify_no_report.xul
@@ -14,35 +14,110 @@
 <embed id="plugin1" type="application/x-test" width="200" height="200"></embed>
 </body>
 <script class="testbody" type="application/javascript">
 <![CDATA[
 SimpleTest.waitForExplicitFinish();
 
 var success = false;
 
+var observerFired = false;
+
+var testObserver = {
+  observe: function(subject, topic, data) {
+    observerFired = true;
+    ok(true, "Observer fired");
+    netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect');
+    is(topic, "plugin-crashed", "Checking correct topic");
+    is(data,  null, "Checking null data");
+    ok((subject instanceof Components.interfaces.nsIPropertyBag2), "got Propbag");
+    ok((subject instanceof Components.interfaces.nsIWritablePropertyBag2),
+"got writable Propbag");
+
+    var id = subject.getPropertyAsAString("minidumpID");
+    isnot(id, "", "got a non-empty crash id");
+    let directoryService =
+      Components.classes["@mozilla.org/file/directory_service;1"].
+      getService(Components.interfaces.nsIProperties);
+    let pendingD = directoryService.get("UAppData",
+                                        Components.interfaces.nsIFile);
+    pendingD.append("Crash Reports");
+    pendingD.append("pending");
+    let dumpFile = pendingD.clone();    
+    dumpFile.append(id + ".dmp");
+    ok(dumpFile.exists(), "minidump exists");
+    let extraFile = pendingD.clone();
+    extraFile.append(id + ".extra");
+    ok(extraFile.exists(), "extra file exists");
+    // cleanup, to be nice
+    dumpFile.remove(false);
+    extraFile.remove(false);
+  },
+
+  QueryInterface: function(iid) {
+    netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect');
+    if (iid.equals(Components.interfaces.nsIObserver) ||
+        iid.equals(Components.interfaces.nsISupportsWeakReference) ||
+        iid.equals(Components.interfaces.nsISupports))
+      return this;
+    throw Components.results.NS_NOINTERFACE;
+  }
+};
+
+
 function onPluginCrashed(aEvent) {
   ok(true, "Plugin crashed notification received");
+  ok(observerFired, "Observer should have fired first");
+  is(aEvent.type, "PluginCrashed", "event is correct type");
 
   var pluginElement = document.getElementById("plugin1");
   is (pluginElement, aEvent.target, "Plugin crashed event target is plugin element");
 
+  netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect');
+  
+  ok(aEvent instanceof Components.interfaces.nsIDOMDataContainerEvent,
+     "plugin crashed event has the right interface");
+  var pluginName = aEvent.getData("pluginName");
+  is(pluginName, "Test Plug-in");
+  var didReport = aEvent.getData("submittedCrashReport");
+  // The app itself may or may not have decided to submit the report, so
+  // allow either true or false here.
+  ok((didReport == true || didReport == false), "event said crash report was submitted");
+
+  var os = Components.classes["@mozilla.org/observer-service;1"].
+           getService(Components.interfaces.nsIObserverService);
+  os.removeObserver(testObserver, "plugin-crashed");
+
+  // re-set MOZ_CRASHREPORTER_NO_REPORT
+  let env = Components.classes["@mozilla.org/process/environment;1"]
+                      .getService(Components.interfaces.nsIEnvironment);
+  env.set("MOZ_CRASHREPORTER_NO_REPORT", "1");
   SimpleTest.finish();
 }
 
 function runTests() {
   netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect');
   var prefs = Components.classes['@mozilla.org/preferences-service;1']
     .getService(Components.interfaces.nsIPrefBranch);
   if (!prefs.getBoolPref('dom.ipc.plugins.enabled')) {
     ok(true, "Skipping this test when IPC plugins are not enabled.");
     SimpleTest.finish();
     return;
   }
+  // the test harness will have set MOZ_CRASHREPORTER_NO_REPORT,
+  // ensure that we can change the setting and have our minidumps
+  // wind up in Crash Reports/pending
+  let env = Components.classes["@mozilla.org/process/environment;1"]
+                      .getService(Components.interfaces.nsIEnvironment);
+  env.set("MOZ_CRASHREPORTER_NO_REPORT", "");
 
+  var os = Components.classes["@mozilla.org/observer-service;1"].
+           getService(Components.interfaces.nsIObserverService);
+  os.addObserver(testObserver, "plugin-crashed", true);
+  
   document.addEventListener("PluginCrashed", onPluginCrashed, false);
 
   var pluginElement = document.getElementById("plugin1");
   try {
     pluginElement.crash();
   } catch (e) {
   }
 }
--- a/netwerk/cache/src/nsDiskCacheStreams.cpp
+++ b/netwerk/cache/src/nsDiskCacheStreams.cpp
@@ -742,17 +742,17 @@ nsDiskCacheStreamIO::FlushBufferToFile()
     return NS_OK;
 }
 
 
 void
 nsDiskCacheStreamIO::DeleteBuffer()
 {
     if (mBuffer) {
-        NS_ASSERTION(mBufDirty == PR_FALSE, "deleting dirty buffer");
+        NS_ASSERTION(!mBufDirty, "deleting dirty buffer");
         free(mBuffer);
         mBuffer = nsnull;
         mBufPos = 0;
         mBufEnd = 0;
         mBufSize = 0;
     }
 }
 
--- a/netwerk/cache/src/nsMemoryCacheDevice.cpp
+++ b/netwerk/cache/src/nsMemoryCacheDevice.cpp
@@ -102,17 +102,17 @@ nsMemoryCacheDevice::Shutdown()
     mMemCacheEntries.Shutdown();
 
     // evict all entries
     nsCacheEntry * entry, * next;
 
     for (int i = kQueueCount - 1; i >= 0; --i) {
         entry = (nsCacheEntry *)PR_LIST_HEAD(&mEvictionList[i]);
         while (entry != &mEvictionList[i]) {
-            NS_ASSERTION(entry->IsInUse() == PR_FALSE, "### shutting down with active entries");
+            NS_ASSERTION(!entry->IsInUse(), "### shutting down with active entries");
             next = (nsCacheEntry *)PR_NEXT_LINK(entry);
             PR_REMOVE_AND_INIT_LINK(entry);
         
             // update statistics
             PRInt32 memoryRecovered = (PRInt32)entry->Size();
             mTotalSize    -= memoryRecovered;
             mInactiveSize -= memoryRecovered;
             --mEntryCount;
--- a/netwerk/cookie/src/nsCookieService.cpp
+++ b/netwerk/cookie/src/nsCookieService.cpp
@@ -1722,21 +1722,17 @@ nsCookieService::AddInternal(const nsCSt
        trivial case, but allows the flexibility of setting only a cookie <VALUE>
        with a blank <NAME> and is required by some sites (see bug 169091).
        
     6. Attribute "HttpOnly", not covered in the RFCs, is supported
        (see bug 178993).
 
  ** Begin BNF:
     token         = 1*<any allowed-chars except separators>
-    value         = token-value | quoted-string
-    token-value   = 1*<any allowed-chars except value-sep>
-    quoted-string = ( <"> *( qdtext | quoted-pair ) <"> )
-    qdtext        = <any allowed-chars except <">>             ; CR | LF removed by necko
-    quoted-pair   = "\" <any OCTET except NUL or cookie-sep>   ; CR | LF removed by necko
+    value         = 1*<any allowed-chars except value-sep>
     separators    = ";" | "="
     value-sep     = ";"
     cookie-sep    = CR | LF
     allowed-chars = <any OCTET except NUL or cookie-sep>
     OCTET         = <any 8-bit sequence of data>
     LWS           = SP | HT
     NUL           = <US-ASCII NUL, null control character (0)>
     CR            = <US-ASCII CR, carriage return (13)>
@@ -1761,17 +1757,16 @@ nsCookieService::AddInternal(const nsCSt
                   | "Secure"
                   | "HttpOnly"
 
 ******************************************************************************/
 
 // helper functions for GetTokenValue
 static inline PRBool iswhitespace     (char c) { return c == ' '  || c == '\t'; }
 static inline PRBool isterminator     (char c) { return c == '\n' || c == '\r'; }
-static inline PRBool isquoteterminator(char c) { return isterminator(c) || c == '"'; }
 static inline PRBool isvalueseparator (char c) { return isterminator(c) || c == ';'; }
 static inline PRBool istokenseparator (char c) { return isvalueseparator(c) || c == '='; }
 
 // Parse a single token/value pair.
 // Returns PR_TRUE if a cookie terminator is found, so caller can parse new cookie.
 PRBool
 nsCookieService::GetTokenValue(nsASingleFragmentCString::const_char_iterator &aIter,
                                nsASingleFragmentCString::const_char_iterator &aEndIter,
@@ -1801,49 +1796,26 @@ nsCookieService::GetTokenValue(nsASingle
 
   aEqualsFound = (*aIter == '=');
   if (aEqualsFound) {
     // find <value>
     while (++aIter != aEndIter && iswhitespace(*aIter));
 
     start = aIter;
 
-    if (*aIter == '"') {
-      // process <quoted-string>
-      // (note: cookie terminators, CR | LF, can't happen:
-      // they're removed by necko before the header gets here)
-      // assume value mangled if no terminating '"', return
-      while (++aIter != aEndIter && !isquoteterminator(*aIter)) {
-        // if <qdtext> (backwhacked char), skip over it. this allows '\"' in <quoted-string>.
-        // we increment once over the backwhack, nullcheck, then continue to the 'while',
-        // which increments over the backwhacked char. one exception - we don't allow
-        // CR | LF here either (see above about necko)
-        if (*aIter == '\\' && (++aIter == aEndIter || isterminator(*aIter)))
-          break;
-      }
-
-      if (aIter != aEndIter && !isterminator(*aIter)) {
-        // include terminating quote in attribute string
-        aTokenValue.Rebind(start, ++aIter);
-        // skip to next ';'
-        while (aIter != aEndIter && !isvalueseparator(*aIter))
-          ++aIter;
-      }
-    } else {
-      // process <token-value>
-      // just look for ';' to terminate ('=' allowed)
-      while (aIter != aEndIter && !isvalueseparator(*aIter))
-        ++aIter;
-
-      // remove trailing <LWS>; first check we're not at the beginning
-      if (aIter != start) {
-        lastSpace = aIter;
-        while (--lastSpace != start && iswhitespace(*lastSpace));
-        aTokenValue.Rebind(start, ++lastSpace);
-      }
+    // process <token>
+    // just look for ';' to terminate ('=' allowed)
+    while (aIter != aEndIter && !isvalueseparator(*aIter))
+      ++aIter;
+
+    // remove trailing <LWS>; first check we're not at the beginning
+    if (aIter != start) {
+      lastSpace = aIter;
+      while (--lastSpace != start && iswhitespace(*lastSpace));
+      aTokenValue.Rebind(start, ++lastSpace);
     }
   }
 
   // aIter is on ';', or terminator, or EOS
   if (aIter != aEndIter) {
     // if on terminator, increment past & return PR_TRUE to process new cookie
     if (isterminator(*aIter)) {
       ++aIter;
@@ -1895,20 +1867,16 @@ nsCookieService::ParseAttributes(nsDepen
 
   // extract remaining attributes
   while (cookieStart != cookieEnd && !newCookie) {
     newCookie = GetTokenValue(cookieStart, cookieEnd, tokenString, tokenValue, equalsFound);
 
     if (!tokenValue.IsEmpty()) {
       tokenValue.BeginReading(tempBegin);
       tokenValue.EndReading(tempEnd);
-      if (*tempBegin == '"' && *--tempEnd == '"') {
-        // our parameter is a quoted-string; remove quotes for later parsing
-        tokenValue.Rebind(++tempBegin, tempEnd);
-      }
     }
 
     // decide which attribute we have, and copy the string
     if (tokenString.LowerCaseEqualsLiteral(kPath))
       aCookieAttributes.path = tokenValue;
 
     else if (tokenString.LowerCaseEqualsLiteral(kDomain))
       aCookieAttributes.host = tokenValue;
@@ -2264,27 +2232,24 @@ nsCookieService::GetExpiry(nsCookieAttri
     if (numInts != 1) {
       return PR_TRUE;
     }
 
     delta = maxage;
 
   // check for expires attribute
   } else if (!aCookieAttributes.expires.IsEmpty()) {
-    PRTime tempExpires;
-    PRInt64 expires;
+    PRTime expires;
 
     // parse expiry time
-    if (PR_ParseTimeString(aCookieAttributes.expires.get(), PR_TRUE, &tempExpires) == PR_SUCCESS) {
-      expires = tempExpires / PR_USEC_PER_SEC;
-    } else {
+    if (PR_ParseTimeString(aCookieAttributes.expires.get(), PR_TRUE, &expires) != PR_SUCCESS) {
       return PR_TRUE;
     }
 
-    delta = expires - aServerTime;
+    delta = expires / PR_USEC_PER_SEC - aServerTime;
 
   // default to session cookie if no attributes found
   } else {
     return PR_TRUE;
   }
 
   // if this addition overflows, expiryTime will be less than currentTime
   // and the cookie will be expired - that's okay.
--- a/netwerk/streamconv/converters/nsDirIndexParser.cpp
+++ b/netwerk/streamconv/converters/nsDirIndexParser.cpp
@@ -310,17 +310,17 @@ nsDirIndexParser::ParseData(nsIDirIndex 
             success = PR_TRUE;
           }
           NS_Free(result);
         } else {
           NS_WARNING("UnEscapeAndConvert error");
         }
       }
       
-      if (success == PR_FALSE) {
+      if (!success) {
         // if unsuccessfully at charset conversion, then
         // just fallback to unescape'ing in-place
         // XXX - this shouldn't be using UTF8, should it?
         // when can we fail to get the service, anyway? - bbaetz
         aIdx->SetLocation(filename.get());
         if (!mHasDescription) {
           aIdx->SetDescription(NS_ConvertUTF8toUTF16(value).get());
         }
--- a/netwerk/streamconv/converters/nsHTTPCompressConv.cpp
+++ b/netwerk/streamconv/converters/nsHTTPCompressConv.cpp
@@ -80,17 +80,17 @@ nsHTTPCompressConv::~nsHTTPCompressConv(
     if (mInpBuffer)
         nsMemory::Free(mInpBuffer);
 
     if (mOutBuffer)
         nsMemory::Free(mOutBuffer);
 
     // For some reason we are not getting Z_STREAM_END.  But this was also seen
     //    for mozilla bug 198133.  Need to handle this case.
-    if ((mStreamInitialized == PR_TRUE) && (mStreamEnded == PR_FALSE))
+    if (mStreamInitialized && !mStreamEnded)
         inflateEnd (&d_stream);
 }
 
 NS_IMETHODIMP
 nsHTTPCompressConv::AsyncConvertData(const char *aFromType, 
                                      const char *aToType, 
                                      nsIStreamListener *aListener, 
                                      nsISupports *aCtxt)
--- a/netwerk/test/TestCookie.cpp
+++ b/netwerk/test/TestCookie.cpp
@@ -57,92 +57,98 @@ static NS_DEFINE_CID(kPrefServiceCID,   
 // various pref strings
 static const char kCookiesPermissions[] = "network.cookie.cookieBehavior";
 static const char kCookiesLifetimeEnabled[] = "network.cookie.lifetime.enabled";
 static const char kCookiesLifetimeDays[] = "network.cookie.lifetime.days";
 static const char kCookiesLifetimeCurrentSession[] = "network.cookie.lifetime.behavior";
 static const char kCookiesP3PString[] = "network.cookie.p3p";
 static const char kCookiesAskPermission[] = "network.cookie.warnAboutCookies";
 
+static char *sBuffer;
+
 nsresult
 SetACookie(nsICookieService *aCookieService, const char *aSpec1, const char *aSpec2, const char* aCookieString, const char *aServerTime)
 {
     nsCOMPtr<nsIURI> uri1, uri2;
     NS_NewURI(getter_AddRefs(uri1), aSpec1);
     if (aSpec2)
         NS_NewURI(getter_AddRefs(uri2), aSpec2);
 
-    printf("    for host \"%s\": SET ", aSpec1);
+    sBuffer = PR_sprintf_append(sBuffer, "    for host \"%s\": SET ", aSpec1);
     nsresult rv = aCookieService->SetCookieStringFromHttp(uri1, uri2, nsnull, (char *)aCookieString, aServerTime, nsnull);
     // the following code is useless. the cookieservice blindly returns NS_OK
     // from SetCookieString. we have to call GetCookie to see if the cookie was
     // set correctly...
     if (NS_FAILED(rv)) {
-        printf("nothing\n");
+        sBuffer = PR_sprintf_append(sBuffer, "nothing\n");
     } else {
-        printf("\"%s\"\n", aCookieString);
+        sBuffer = PR_sprintf_append(sBuffer, "\"%s\"\n", aCookieString);
     }
     return rv;
 }
 
 nsresult
 SetACookieNoHttp(nsICookieService *aCookieService, const char *aSpec, const char* aCookieString)
 {
     nsCOMPtr<nsIURI> uri;
     NS_NewURI(getter_AddRefs(uri), aSpec);
 
-    printf("    for host \"%s\": SET ", aSpec);
+    sBuffer = PR_sprintf_append(sBuffer, "    for host \"%s\": SET ", aSpec);
     nsresult rv = aCookieService->SetCookieString(uri, nsnull, (char *)aCookieString, nsnull);
     // the following code is useless. the cookieservice blindly returns NS_OK
     // from SetCookieString. we have to call GetCookie to see if the cookie was
     // set correctly...
     if (NS_FAILED(rv)) {
-        printf("nothing\n");
+        sBuffer = PR_sprintf_append(sBuffer, "nothing\n");
     } else {
-        printf("\"%s\"\n", aCookieString);
+        sBuffer = PR_sprintf_append(sBuffer, "\"%s\"\n", aCookieString);
     }
     return rv;
 }
 
 // returns PR_TRUE if cookie(s) for the given host were found; else PR_FALSE.
 // the cookie string is returned via aCookie.
 PRBool
 GetACookie(nsICookieService *aCookieService, const char *aSpec1, const char *aSpec2, char **aCookie)
 {
     nsCOMPtr<nsIURI> uri1, uri2;
     NS_NewURI(getter_AddRefs(uri1), aSpec1);
     if (aSpec2)
         NS_NewURI(getter_AddRefs(uri2), aSpec2);
 
-    printf("             \"%s\": GOT ", aSpec1);
+    sBuffer = PR_sprintf_append(sBuffer, "             \"%s\": GOT ", aSpec1);
     nsresult rv = aCookieService->GetCookieStringFromHttp(uri1, uri2, nsnull, aCookie);
-    if (NS_FAILED(rv)) printf("XXX GetCookieString() failed!\n");
+    if (NS_FAILED(rv)) {
+      sBuffer = PR_sprintf_append(sBuffer, "XXX GetCookieString() failed!\n");
+    }
     if (!*aCookie) {
-        printf("nothing\n");
+        sBuffer = PR_sprintf_append(sBuffer, "nothing\n");
     } else {
-        printf("\"%s\"\n", *aCookie);
+        sBuffer = PR_sprintf_append(sBuffer, "\"%s\"\n", *aCookie);
     }
     return *aCookie != nsnull;
 }
 
 // returns PR_TRUE if cookie(s) for the given host were found; else PR_FALSE.
 // the cookie string is returned via aCookie.
 PRBool
 GetACookieNoHttp(nsICookieService *aCookieService, const char *aSpec, char **aCookie)
 {
     nsCOMPtr<nsIURI> uri;
     NS_NewURI(getter_AddRefs(uri), aSpec);
 
-    printf("             \"%s\": GOT ", aSpec);
+    sBuffer = PR_sprintf_append(sBuffer, "             \"%s\": GOT ", aSpec);
     nsresult rv = aCookieService->GetCookieString(uri, nsnull, aCookie);
-    if (NS_FAILED(rv)) printf("XXX GetCookieString() failed!\n");
+    if (NS_FAILED(rv)) {
+      sBuffer = PR_sprintf_append(sBuffer, "XXX GetCookieString() failed!\n");
+    }
     if (!*aCookie) {
-        printf("nothing\n");
+        sBuffer = PR_sprintf_append(sBuffer, "nothing\n");
     } else {
-        printf("\"%s\"\n", *aCookie);
+        sBuffer = PR_sprintf_append(sBuffer, "\"%s\"\n", *aCookie);
     }
     return *aCookie != nsnull;
 }
 
 // some #defines for comparison rules
 #define MUST_BE_NULL     0
 #define MUST_EQUAL       1
 #define MUST_CONTAIN     2
@@ -178,27 +184,27 @@ CheckResult(const char *aLhs, PRUint32 a
 
 // helper function that ensures the first aSize elements of aResult are
 // PR_TRUE (i.e. all tests succeeded). prints the result of the tests (if any
 // tests failed, it prints the zero-based index of each failed test).
 PRBool
 PrintResult(const PRBool aResult[], PRUint32 aSize)
 {
     PRBool failed = PR_FALSE;
-    printf("*** tests ");
+    sBuffer = PR_sprintf_append(sBuffer, "*** tests ");
     for (PRUint32 i = 0; i < aSize; ++i) {
         if (!aResult[i]) {
             failed = PR_TRUE;
-            printf("%d ", i);
+            sBuffer = PR_sprintf_append(sBuffer, "%d ", i);
         }
     }
     if (failed) {
-        printf("FAILED!\a\n");
+        sBuffer = PR_sprintf_append(sBuffer, "FAILED!\a\n");
     } else {
-        printf("passed.\n");
+        sBuffer = PR_sprintf_append(sBuffer, "passed.\n");
     }
     return !failed;
 }
 
 void
 InitPrefs(nsIPrefBranch *aPrefBranch)
 {
     // init some relevant prefs, so the tests don't go awry.
@@ -247,25 +253,16 @@ main(PRInt32 argc, char *argv[])
         do_GetService(kPrefServiceCID, &rv0);
       if (NS_FAILED(rv0)) return -1;
 
       InitPrefs(prefBranch);
 
       PRBool rv[20];
       nsCString cookie;
 
-      // call NS_NewURI just to force chrome registrations, so all our
-      // printf'ed messages are together.
-      {
-        nsCOMPtr<nsIURI> foo;
-        NS_NewURI(getter_AddRefs(foo), "http://foo.com");
-      }
-      printf("\n");
-
-
       /* The basic idea behind these tests is the following:
        *
        * we set() some cookie, then try to get() it in various ways. we have
        * several possible tests we perform on the cookie string returned from
        * get():
        *
        * a) check whether the returned string is null (i.e. we got no cookies
        *    back). this is used e.g. to ensure a given cookie was deleted
@@ -295,17 +292,17 @@ main(PRInt32 argc, char *argv[])
        * of rv (i.e. zero-based). at the conclusion of all tests, the overall
        * passed/failed result is printed.
        *
        * NOTE: this testsuite is not yet comprehensive or complete, and is
        * somewhat contrived - still under development, and needs improving!
        */
 
       // *** basic tests
-      printf("*** Beginning basic tests...\n");
+      sBuffer = PR_sprintf_append(sBuffer, "*** Beginning basic tests...\n");
 
       // test some basic variations of the domain & path
       SetACookie(cookieService, "http://www.basic.com", nsnull, "test=basic", nsnull);
       GetACookie(cookieService, "http://www.basic.com", nsnull, getter_Copies(cookie));
       rv[0] = CheckResult(cookie.get(), MUST_EQUAL, "test=basic");
       GetACookie(cookieService, "http://www.basic.com/testPath/testfile.txt", nsnull, getter_Copies(cookie));
       rv[1] = CheckResult(cookie.get(), MUST_EQUAL, "test=basic");
       GetACookie(cookieService, "http://www.basic.com./", nsnull, getter_Copies(cookie));
@@ -319,17 +316,17 @@ main(PRInt32 argc, char *argv[])
       SetACookie(cookieService, "http://www.basic.com", nsnull, "test=basic; max-age=-1", nsnull);
       GetACookie(cookieService, "http://www.basic.com/", nsnull, getter_Copies(cookie));
       rv[6] = CheckResult(cookie.get(), MUST_BE_NULL);
 
       allTestsPassed = PrintResult(rv, 7) && allTestsPassed;
 
 
       // *** domain tests
-      printf("*** Beginning domain tests...\n");
+      sBuffer = PR_sprintf_append(sBuffer, "*** Beginning domain tests...\n");
 
       // test some variations of the domain & path, for different domains of
       // a domain cookie
       SetACookie(cookieService, "http://www.domain.com", nsnull, "test=domain; domain=domain.com", nsnull);
       GetACookie(cookieService, "http://domain.com", nsnull, getter_Copies(cookie));
       rv[0] = CheckResult(cookie.get(), MUST_EQUAL, "test=domain");
       GetACookie(cookieService, "http://domain.com.", nsnull, getter_Copies(cookie));
       rv[1] = CheckResult(cookie.get(), MUST_EQUAL, "test=domain");
@@ -371,17 +368,17 @@ main(PRInt32 argc, char *argv[])
       SetACookie(cookieService, "http://www.domain.com", nsnull, "test=domain; domain=..domain.com.", nsnull);
       GetACookie(cookieService, "http://foo.domain.com", nsnull, getter_Copies(cookie));
       rv[13] = CheckResult(cookie.get(), MUST_BE_NULL);
 
       allTestsPassed = PrintResult(rv, 14) && allTestsPassed;
 
 
       // *** path tests
-      printf("*** Beginning path tests...\n");
+      sBuffer = PR_sprintf_append(sBuffer, "*** Beginning path tests...\n");
 
       // test some variations of the domain & path, for different paths of
       // a path cookie
       SetACookie(cookieService, "http://path.net/path/file", nsnull, "test=path; path=/path", nsnull);
       GetACookie(cookieService, "http://path.net/path", nsnull, getter_Copies(cookie));
       rv[0] = CheckResult(cookie.get(), MUST_EQUAL, "test=path");
       GetACookie(cookieService, "http://path.net/path/", nsnull, getter_Copies(cookie));
       rv[1] = CheckResult(cookie.get(), MUST_EQUAL, "test=path");
@@ -444,66 +441,75 @@ main(PRInt32 argc, char *argv[])
       GetACookie(cookieService, "http://path.net/", nsnull, getter_Copies(cookie));
       rv[18] = CheckResult(cookie.get(), MUST_BE_NULL);
 
       allTestsPassed = PrintResult(rv, 19) && allTestsPassed;
 
 
       // *** expiry & deletion tests
       // XXX add server time str parsing tests here
-      printf("*** Beginning expiry & deletion tests...\n");
+      sBuffer = PR_sprintf_append(sBuffer, "*** Beginning expiry & deletion tests...\n");
 
       // test some variations of the expiry time,
       // and test deletion of previously set cookies
       SetACookie(cookieService, "http://expireme.org/", nsnull, "test=expiry; max-age=-1", nsnull);
       GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
       rv[0] = CheckResult(cookie.get(), MUST_BE_NULL);
       SetACookie(cookieService, "http://expireme.org/", nsnull, "test=expiry; max-age=0", nsnull);
       GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
       rv[1] = CheckResult(cookie.get(), MUST_BE_NULL);
+      SetACookie(cookieService, "http://expireme.org/", nsnull, "test=expiry; expires=bad", nsnull);
+      GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
+      rv[2] = CheckResult(cookie.get(), MUST_EQUAL, "test=expiry");
       SetACookie(cookieService, "http://expireme.org/", nsnull, "test=expiry; expires=Thu, 10 Apr 1980 16:33:12 GMT", nsnull);
       GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
-      rv[2] = CheckResult(cookie.get(), MUST_BE_NULL);
+      rv[3] = CheckResult(cookie.get(), MUST_BE_NULL);
+      SetACookie(cookieService, "http://expireme.org/", nsnull, "test=expiry; expires=\"Thu, 10 Apr 1980 16:33:12 GMT", nsnull);
+      GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
+      rv[4] = CheckResult(cookie.get(), MUST_BE_NULL);
+      SetACookie(cookieService, "http://expireme.org/", nsnull, "test=expiry; expires=\"Thu, 10 Apr 1980 16:33:12 GMT\"", nsnull);
+      GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
+      rv[5] = CheckResult(cookie.get(), MUST_BE_NULL);
 
       SetACookie(cookieService, "http://expireme.org/", nsnull, "test=expiry; max-age=60", nsnull);
       GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
-      rv[3] = CheckResult(cookie.get(), MUST_EQUAL, "test=expiry");
+      rv[6] = CheckResult(cookie.get(), MUST_EQUAL, "test=expiry");
       SetACookie(cookieService, "http://expireme.org/", nsnull, "test=expiry; max-age=-20", nsnull);
       GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
-      rv[4] = CheckResult(cookie.get(), MUST_BE_NULL);
+      rv[7] = CheckResult(cookie.get(), MUST_BE_NULL);
       SetACookie(cookieService, "http://expireme.org/", nsnull, "test=expiry; max-age=60", nsnull);
       GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
-      rv[5] = CheckResult(cookie.get(), MUST_EQUAL, "test=expiry");
+      rv[8] = CheckResult(cookie.get(), MUST_EQUAL, "test=expiry");
       SetACookie(cookieService, "http://expireme.org/", nsnull, "test=expiry; expires=Thu, 10 Apr 1980 16:33:12 GMT", nsnull);
       GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
-      rv[6] = CheckResult(cookie.get(), MUST_BE_NULL);
+      rv[9] = CheckResult(cookie.get(), MUST_BE_NULL);
       SetACookie(cookieService, "http://expireme.org/", nsnull, "test=expiry; max-age=60", nsnull);
       SetACookie(cookieService, "http://expireme.org/", nsnull, "newtest=expiry; max-age=60", nsnull);
       GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
-      rv[7] = CheckResult(cookie.get(), MUST_CONTAIN, "test=expiry");
-      rv[8] = CheckResult(cookie.get(), MUST_CONTAIN, "newtest=expiry");
+      rv[10] = CheckResult(cookie.get(), MUST_CONTAIN, "test=expiry");
+      rv[11] = CheckResult(cookie.get(), MUST_CONTAIN, "newtest=expiry");
       SetACookie(cookieService, "http://expireme.org/", nsnull, "test=differentvalue; max-age=0", nsnull);
       GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
-      rv[9] = CheckResult(cookie.get(), MUST_EQUAL, "newtest=expiry");
+      rv[12] = CheckResult(cookie.get(), MUST_EQUAL, "newtest=expiry");
       SetACookie(cookieService, "http://expireme.org/", nsnull, "newtest=evendifferentvalue; max-age=0", nsnull);
       GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
-      rv[10] = CheckResult(cookie.get(), MUST_BE_NULL);
+      rv[13] = CheckResult(cookie.get(), MUST_BE_NULL);
 
       SetACookie(cookieService, "http://foo.expireme.org/", nsnull, "test=expiry; domain=.expireme.org; max-age=60", nsnull);
       GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
-      rv[11] = CheckResult(cookie.get(), MUST_EQUAL, "test=expiry");
+      rv[14] = CheckResult(cookie.get(), MUST_EQUAL, "test=expiry");
       SetACookie(cookieService, "http://bar.expireme.org/", nsnull, "test=differentvalue; domain=.expireme.org; max-age=0", nsnull);
       GetACookie(cookieService, "http://expireme.org/", nsnull, getter_Copies(cookie));
-      rv[12] = CheckResult(cookie.get(), MUST_BE_NULL);
+      rv[15] = CheckResult(cookie.get(), MUST_BE_NULL);
 
-      allTestsPassed = PrintResult(rv, 13) && allTestsPassed;
+      allTestsPassed = PrintResult(rv, 16) && allTestsPassed;
 
 
       // *** multiple cookie tests
-      printf("*** Beginning multiple cookie tests...\n");
+      sBuffer = PR_sprintf_append(sBuffer, "*** Beginning multiple cookie tests...\n");
 
       // test the setting of multiple cookies, and test the order of precedence
       // (a later cookie overwriting an earlier one, in the same header string)
       SetACookie(cookieService, "http://multiple.cookies/", nsnull, "test=multiple; domain=.multiple.cookies \n test=different \n test=same; domain=.multiple.cookies \n newtest=ciao \n newtest=foo; max-age=-6 \n newtest=reincarnated", nsnull);
       GetACookie(cookieService, "http://multiple.cookies/", nsnull, getter_Copies(cookie));
       rv[0] = CheckResult(cookie.get(), MUST_NOT_CONTAIN, "test=multiple");
       rv[1] = CheckResult(cookie.get(), MUST_CONTAIN, "test=different");
       rv[2] = CheckResult(cookie.get(), MUST_CONTAIN, "test=same");
@@ -519,28 +525,28 @@ main(PRInt32 argc, char *argv[])
       SetACookie(cookieService, "http://multiple.cookies/", nsnull,  "newtest=dead; max-age=0", nsnull);
       GetACookie(cookieService, "http://multiple.cookies/", nsnull, getter_Copies(cookie));
       rv[8] = CheckResult(cookie.get(), MUST_BE_NULL);
 
       allTestsPassed = PrintResult(rv, 9) && allTestsPassed;
 
 
       // *** parser tests
-      printf("*** Beginning parser tests...\n");
+      sBuffer = PR_sprintf_append(sBuffer, "*** Beginning parser tests...\n");
 
       // test the cookie header parser, under various circumstances.
       SetACookie(cookieService, "http://parser.test/", nsnull, "test=parser; domain=.parser.test; ;; ;=; ,,, ===,abc,=; abracadabra! max-age=20;=;;", nsnull);
       GetACookie(cookieService, "http://parser.test/", nsnull, getter_Copies(cookie));
       rv[0] = CheckResult(cookie.get(), MUST_EQUAL, "test=parser");
       SetACookie(cookieService, "http://parser.test/", nsnull, "test=parser; domain=.parser.test; max-age=0", nsnull);
       GetACookie(cookieService, "http://parser.test/", nsnull, getter_Copies(cookie));
       rv[1] = CheckResult(cookie.get(), MUST_BE_NULL);
       SetACookie(cookieService, "http://parser.test/", nsnull, "test=\"fubar! = foo;bar\\\";\" parser; domain=.parser.test; max-age=6\nfive; max-age=2.63,", nsnull);
       GetACookie(cookieService, "http://parser.test/", nsnull, getter_Copies(cookie));
-      rv[2] = CheckResult(cookie.get(), MUST_CONTAIN, "test=\"fubar! = foo;bar\\\";\"");
+      rv[2] = CheckResult(cookie.get(), MUST_CONTAIN, "test=\"fubar! = foo");
       rv[3] = CheckResult(cookie.get(), MUST_CONTAIN, "five");
       SetACookie(cookieService, "http://parser.test/", nsnull, "test=kill; domain=.parser.test; max-age=0 \n five; max-age=0", nsnull);
       GetACookie(cookieService, "http://parser.test/", nsnull, getter_Copies(cookie));
       rv[4] = CheckResult(cookie.get(), MUST_BE_NULL);
 
       // test the handling of VALUE-only cookies (see bug 169091),
       // i.e. "six" should assume an empty NAME, which allows other VALUE-only
       // cookies to overwrite it
@@ -556,17 +562,17 @@ main(PRInt32 argc, char *argv[])
       SetACookie(cookieService, "http://parser.test/", nsnull, "test=six", nsnull);
       GetACookie(cookieService, "http://parser.test/", nsnull, getter_Copies(cookie));
       rv[9] = CheckResult(cookie.get(), MUST_CONTAIN, "test=six");
 
       allTestsPassed = PrintResult(rv, 10) && allTestsPassed;
 
 
       // *** mailnews tests
-      printf("*** Beginning mailnews tests...\n");
+      sBuffer = PR_sprintf_append(sBuffer, "*** Beginning mailnews tests...\n");
 
       // test some mailnews cookies to ensure blockage.
       // we use null firstURI's deliberately, since we have hacks to deal with
       // this situation...
       SetACookie(cookieService, "mailbox://mail.co.uk/", nsnull, "test=mailnews", nsnull);
       GetACookie(cookieService, "mailbox://mail.co.uk/", nsnull, getter_Copies(cookie));
       rv[0] = CheckResult(cookie.get(), MUST_BE_NULL);
       GetACookie(cookieService, "http://mail.co.uk/", nsnull, getter_Copies(cookie));
@@ -579,33 +585,33 @@ main(PRInt32 argc, char *argv[])
       SetACookie(cookieService, "http://mail.co.uk/", nsnull, "test=mailnews; max-age=0", nsnull);
       GetACookie(cookieService, "http://mail.co.uk/", nsnull, getter_Copies(cookie));
       rv[4] = CheckResult(cookie.get(), MUST_BE_NULL);
 
       allTestsPassed = PrintResult(rv, 5) && allTestsPassed;
 
 
       // *** path ordering tests
-      printf("*** Beginning path ordering tests...\n");
+      sBuffer = PR_sprintf_append(sBuffer, "*** Beginning path ordering tests...\n");
 
       // test that cookies are returned in path order - longest to shortest.
       // if the header doesn't specify a path, it's taken from the host URI.
       SetACookie(cookieService, "http://multi.path.tests/", nsnull, "test1=path; path=/one/two/three", nsnull);
       SetACookie(cookieService, "http://multi.path.tests/", nsnull, "test2=path; path=/one \n test3=path; path=/one/two/three/four \n test4=path; path=/one/two \n test5=path; path=/one/two/", nsnull);
       SetACookie(cookieService, "http://multi.path.tests/one/two/three/four/five/", nsnull, "test6=path", nsnull);
       SetACookie(cookieService, "http://multi.path.tests/one/two/three/four/five/six/", nsnull, "test7=path; path=", nsnull);
       SetACookie(cookieService, "http://multi.path.tests/", nsnull, "test8=path; path=/", nsnull);
       GetACookie(cookieService, "http://multi.path.tests/one/two/three/four/five/six/", nsnull, getter_Copies(cookie));
       rv[0] = CheckResult(cookie.get(), MUST_EQUAL, "test7=path; test6=path; test3=path; test1=path; test5=path; test4=path; test2=path; test8=path");
 
       allTestsPassed = PrintResult(rv, 1) && allTestsPassed;
 
 
       // *** httponly tests 
-      printf("*** Beginning httponly tests...\n");
+      sBuffer = PR_sprintf_append(sBuffer, "*** Beginning httponly tests...\n");
 
       // Since this cookie is NOT set via http, setting it fails
       SetACookieNoHttp(cookieService, "http://httponly.test/", "test=httponly; httponly");
       GetACookie(cookieService, "http://httponly.test/", nsnull, getter_Copies(cookie));
       rv[0] = CheckResult(cookie.get(), MUST_BE_NULL);
       // Since this cookie is set via http, it can be retrieved
       SetACookie(cookieService, "http://httponly.test/", nsnull, "test=httponly; httponly", nsnull);
       GetACookie(cookieService, "http://httponly.test/", nsnull, getter_Copies(cookie));
@@ -640,17 +646,17 @@ main(PRInt32 argc, char *argv[])
       SetACookieNoHttp(cookieService, "http://httponly.test/", "test=httponly; httponly");
       GetACookieNoHttp(cookieService, "http://httponly.test/", getter_Copies(cookie));
       rv[8] = CheckResult(cookie.get(), MUST_EQUAL, "test=not-httponly");
 
       allTestsPassed = PrintResult(rv, 9) && allTestsPassed;
 
 
       // *** nsICookieManager{2} interface tests
-      printf("*** Beginning nsICookieManager{2} interface tests...\n");
+      sBuffer = PR_sprintf_append(sBuffer, "*** Beginning nsICookieManager{2} interface tests...\n");
       nsCOMPtr<nsICookieManager> cookieMgr = do_GetService(NS_COOKIEMANAGER_CONTRACTID, &rv0);
       if (NS_FAILED(rv0)) return -1;
       nsCOMPtr<nsICookieManager2> cookieMgr2 = do_QueryInterface(cookieMgr);
       if (!cookieMgr2) return -1;
       
       // first, ensure a clean slate
       rv[0] = NS_SUCCEEDED(cookieMgr->RemoveAll());
       // add some cookies
@@ -738,17 +744,17 @@ main(PRInt32 argc, char *argv[])
       rv[17] = NS_SUCCEEDED(cookieMgr->GetEnumerator(getter_AddRefs(enumerator))) &&
                NS_SUCCEEDED(enumerator->HasMoreElements(&more)) &&
                !more;
 
       allTestsPassed = PrintResult(rv, 18) && allTestsPassed;
 
 
       // *** eviction and creation ordering tests
-      printf("*** Beginning eviction and creation ordering tests...\n");
+      sBuffer = PR_sprintf_append(sBuffer, "*** Beginning eviction and creation ordering tests...\n");
 
       // test that cookies are
       // a) returned by order of creation time (oldest first, newest last)
       // b) evicted by order of lastAccessed time, if the limit on cookies per host (50) is reached
       nsCAutoString name;
       nsCAutoString expected;
       for (PRInt32 i = 0; i < 60; ++i) {
         name = NS_LITERAL_CSTRING("test");
@@ -775,14 +781,22 @@ main(PRInt32 argc, char *argv[])
 
 
       // XXX the following are placeholders: add these tests please!
       // *** "noncompliant cookie" tests
       // *** IP address tests
       // *** speed tests
 
 
-      printf("\n*** Result: %s!\n\n", allTestsPassed ? "all tests passed" : "TEST(S) FAILED");
-
+      sBuffer = PR_sprintf_append(sBuffer, "\n*** Result: %s!\n\n", allTestsPassed ? "all tests passed" : "TEST(S) FAILED");
     }
-    
-    return allTestsPassed ? 0 : 1;
+
+    if (!allTestsPassed) {
+      // print the entire log
+      printf("%s", sBuffer);
+      return 1;
+    }
+
+    PR_smprintf_free(sBuffer);
+    sBuffer = nsnull;
+
+    return 0;
 }
--- a/netwerk/test/httpserver/httpd.js
+++ b/netwerk/test/httpserver/httpd.js
@@ -52,16 +52,19 @@ const Cr = Components.results;
 const Cu = Components.utils;
 const CC = Components.Constructor;
 
 const PR_UINT32_MAX = Math.pow(2, 32) - 1;
 
 /** True if debugging output is enabled, false otherwise. */
 var DEBUG = false; // non-const *only* so tweakable in server tests
 
+/** True if debugging output should be timestamped. */
+var DEBUG_TIMESTAMP = false; // non-const so tweakable in server tests
+
 var gGlobalObject = this;
 
 /**
  * Asserts that the given condition holds.  If it doesn't, the given message is
  * dumped, a stack trace is printed, and an exception is thrown to attempt to
  * stop execution (which unfortunately must rely upon the exception not being
  * accidentally swallowed by the code that uses it).
  */
@@ -70,17 +73,17 @@ function NS_ASSERT(cond, msg)
   if (DEBUG && !cond)
   {
     dumpn("###!!!");
     dumpn("###!!! ASSERTION" + (msg ? ": " + msg : "!"));
     dumpn("###!!! Stack follows:");
 
     var stack = new Error().stack.split(/\n/);
     dumpn(stack.map(function(val) { return "###!!!   " + val; }).join("\n"));
-    
+
     throw Cr.NS_ERROR_ABORT;
   }
 }
 
 /** Constructs an HTTP error object. */
 function HttpError(code, description)
 {
   this.code = code;
@@ -159,22 +162,42 @@ const HIDDEN_CHAR = "^";
  * The file name suffix indicating the file containing overridden headers for
  * a requested file.
  */
 const HEADERS_SUFFIX = HIDDEN_CHAR + "headers" + HIDDEN_CHAR;
 
 /** Type used to denote SJS scripts for CGI-like functionality. */
 const SJS_TYPE = "sjs";
 
-
-/** dump(str) with a trailing "\n" -- only outputs if DEBUG */
+/** Base for relative timestamps produced by dumpn(). */
+var firstStamp = 0;
+
+/** dump(str) with a trailing "\n" -- only outputs if DEBUG. */
 function dumpn(str)
 {
   if (DEBUG)
-    dump(str + "\n");
+  {
+    var prefix = "HTTPD-INFO | ";
+    if (DEBUG_TIMESTAMP)
+    {
+      if (firstStamp === 0)
+        firstStamp = Date.now();
+
+      var elapsed = Date.now() - firstStamp; // milliseconds
+      var min = Math.floor(elapsed / 60000);
+      var sec = (elapsed % 60000) / 1000;
+
+      if (sec < 10)
+        prefix += min + ":0" + sec.toFixed(3) + " | ";
+      else
+        prefix += min + ":" + sec.toFixed(3) + " | ";
+    }
+
+    dump(prefix + str + "\n");
+  }
 }
 
 /** Dumps the current JS stack if DEBUG. */
 function dumpStack()
 {
   // peel off the frames for dumpStack() and Error()
   var stack = new Error().stack.split(/\n/).slice(2);
   stack.forEach(dumpn);
--- a/netwerk/wifi/src/nsWifiScannerMac.cpp
+++ b/netwerk/wifi/src/nsWifiScannerMac.cpp
@@ -123,17 +123,17 @@ nsWifiMonitor::DoScanWithCoreWLAN()
     }
 
     // wait for some reasonable amount of time.  pref?
     LOG(("waiting on monitor\n"));
     
     nsAutoMonitor mon(mMonitor);
     mon.Wait(PR_SecondsToInterval(60));
   }
-  while (mKeepGoing == PR_TRUE);
+  while (mKeepGoing);
   
   return NS_OK;
 }
 
 nsresult
 nsWifiMonitor::DoScanOld()
 {
   void *apple_80211_library = dlopen(
@@ -259,17 +259,17 @@ nsWifiMonitor::DoScanOld()
     }
 
     // wait for some reasonable amount of time.  pref?
     LOG(("waiting on monitor\n"));
     
     nsAutoMonitor mon(mMonitor);
     mon.Wait(PR_SecondsToInterval(60));
   }
-  while (mKeepGoing == PR_TRUE);
+  while (mKeepGoing);
   
   (*WirelessDetach_function_)(wifi_context_);
   
   dlclose(apple_80211_library);
   
   return NS_OK;
 }
 
--- a/netwerk/wifi/src/nsWifiScannerUnix.cpp
+++ b/netwerk/wifi/src/nsWifiScannerUnix.cpp
@@ -156,17 +156,17 @@ nsWifiMonitor::DoScan()
     return NS_ERROR_FAILURE;
   }
 
   nsCOMArray<nsWifiAccessPoint> lastAccessPoints;
   nsCOMArray<nsWifiAccessPoint> accessPoints;
 
   char* args[] = {(char*) &accessPoints, (char*) iw_stats, nsnull };
  
-  while (mKeepGoing == PR_TRUE) {
+  while (mKeepGoing) {
 
     accessPoints.Clear();
 
     (*iw_enum)(skfd, &scan_wifi, args, 1);
     
     PRBool accessPointsChanged = !AccessPointsEqual(accessPoints, lastAccessPoints);
     nsCOMArray<nsIWifiListener> currentListeners;
 
--- a/netwerk/wifi/src/nsWifiScannerWin.cpp
+++ b/netwerk/wifi/src/nsWifiScannerWin.cpp
@@ -540,17 +540,17 @@ nsWifiMonitor::DoScan()
     }
     
     // wait for some reasonable amount of time.  pref?
     LOG(("waiting on monitor\n"));
     
     nsAutoMonitor mon(mMonitor);
     mon.Wait(PR_SecondsToInterval(60));
   }
-  while (mKeepGoing == PR_TRUE);
+  while (mKeepGoing);
 
 
 
 #ifdef WINCE
     //Clean up
     CloseHandle(ndis_handle);
 #else
   }
@@ -697,13 +697,13 @@ nsWifiMonitor::DoScan()
       }
       
       // wait for some reasonable amount of time.  pref?
       LOG(("waiting on monitor\n"));
       
       nsAutoMonitor mon(mMonitor);
       mon.Wait(PR_SecondsToInterval(60));
     }
-    while (mKeepGoing == PR_TRUE);
+    while (mKeepGoing);
   }
 #endif
   return NS_OK;
 }
--- a/nsprpub/configure
+++ b/nsprpub/configure
@@ -3368,17 +3368,17 @@ EOF
     STRIP="$STRIP -x -S"
     DLL_SUFFIX=dylib
     USE_PTHREADS=1
     MDCPUCFG_H=_darwin.cfg
     PR_MD_CSRCS=darwin.c
     PR_MD_ASFILES=os_Darwin.s
 
     # Add Mac OS X support for loading CFM & CFBundle plugins
-    if test -f /System/Library/Frameworks/Carbon.framework/Carbon; then
+    if test -f "${MACOS_SDK_DIR}/System/Library/Frameworks/Carbon.framework/Carbon"; then
         cat >> confdefs.h <<\EOF
 #define XP_MACOSX 1
 EOF
 
         OS_TARGET=MacOSX
 
         if test -n "$_MACOSX_DEPLOYMENT_TARGET" ; then
                         export MACOSX_DEPLOYMENT_TARGET=$_MACOSX_DEPLOYMENT_TARGET
@@ -4127,76 +4127,44 @@ EOF
 
     case "$target_cpu" in
     i*86)
 	if test -n "$USE_64"; then
 	    cat >> confdefs.h <<\EOF
 #define _AMD64_ 1
 EOF
 
-	    cat >> confdefs.h <<\EOF
-#define _M_AMD64 1
-EOF
-    
 	else		
 	    cat >> confdefs.h <<\EOF
 #define _X86_ 1
 EOF
 
 	fi
         ;;
-    alpha)
-	    cat >> confdefs.h <<\EOF
-#define _ALPHA_ 1
-EOF
-
-   	    ;;
-    mips)
-	    cat >> confdefs.h <<\EOF
-#define _MIPS_ 1
-EOF
-
-	    ;;
     x86_64)
 	    cat >> confdefs.h <<\EOF
 #define _AMD64_ 1
 EOF
 
-	    cat >> confdefs.h <<\EOF
-#define _M_AMD64 1
-EOF
-
 	    USE_64=1
 	    ;;
     ia64)
 	    cat >> confdefs.h <<\EOF
 #define _IA64_ 1
 EOF
 
-	    cat >> confdefs.h <<\EOF
-#define _M_IA64 1
-EOF
-
 	    USE_64=1
 	    ;;
     *)
 	    cat >> confdefs.h <<\EOF
 #define _CPU_ARCH_NOT_DEFINED 1
 EOF
 
 	    ;;
     esac
-
-    if test "$USE_64"; then
-        cat >> confdefs.h <<\EOF
-#define _WIN64 1
-EOF
-
-    fi
-
     ;;
 
 *-wince*|*-winmo*)
     cat >> confdefs.h <<\EOF
 #define XP_PC 1
 EOF
 
     cat >> confdefs.h <<\EOF
@@ -4503,27 +4471,27 @@ EOF
     if test -z "$GNU_CC"; then
         CC="$CC -std1 -ieee_with_inexact"
         if test "$OS_RELEASE" != "V2.0"; then
             CC="$CC -readonly_strings"
         fi
         _OPTIMIZE_FLAGS="$_OPTIMIZE_FLAGS -Olimit 4000"
         ac_safe=`echo "machine/builtins.h" | sed 'y%./+-%__p_%'`
 echo $ac_n "checking for machine/builtins.h""... $ac_c" 1>&6
-echo "configure:4512: checking for machine/builtins.h" >&5
+echo "configure:4480: checking for machine/builtins.h" >&5
 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then
   echo $ac_n "(cached) $ac_c" 1>&6
 else
   cat > conftest.$ac_ext <<EOF
-#line 4517 "configure"
+#line 4485 "configure"
 #include "confdefs.h"
 #include <machine/builtins.h>
 EOF
 ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out"
-{ (eval echo configure:4522: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
+{ (eval echo configure:4490: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
 ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"`
 if test -z "$ac_err"; then
   rm -rf conftest*
   eval "ac_cv_header_$ac_safe=yes"
 else
   echo "$ac_err" >&5
   echo "configure: failed program was:" >&5
   cat conftest.$ac_ext >&5
@@ -5162,63 +5130,63 @@ if test -z "$SKIP_LIBRARY_CHECKS"; then
 
 
 
 case $target in
 *-darwin*|*-beos*|*-os2*)
     ;;
 *)
     echo $ac_n "checking for dlopen in -ldl""... $ac_c" 1>&6
-echo "configure:5171: checking for dlopen in -ldl" >&5
+echo "configure:5139: checking for dlopen in -ldl" >&5
 ac_lib_var=`echo dl'_'dlopen | sed 'y%./+-%__p_%'`
 if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then
   echo $ac_n "(cached) $ac_c" 1>&6
 else
   ac_save_LIBS="$LIBS"
 LIBS="-ldl  $LIBS"
 cat > conftest.$ac_ext <<EOF
-#line 5179 "configure"
+#line 5147 "configure"
 #include "confdefs.h"
 /* Override any gcc2 internal prototype to avoid an error.  */
 /* We use char because int might match the return type of a gcc2
     builtin and then its argument prototype would still apply.  */
 char dlopen();
 
 int main() {
 dlopen()
 ; return 0; }
 EOF
-if { (eval echo configure:5190: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then
+if { (eval echo configure:5158: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then
   rm -rf conftest*
   eval "ac_cv_lib_$ac_lib_var=yes"
 else
   echo "configure: failed program was:" >&5
   cat conftest.$ac_ext >&5
   rm -rf conftest*
   eval "ac_cv_lib_$ac_lib_var=no"
 fi
 rm -f conftest*
 LIBS="$ac_save_LIBS"
 
 fi
 if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then
   echo "$ac_t""yes" 1>&6
   ac_safe=`echo "dlfcn.h" | sed 'y%./+-%__p_%'`
 echo $ac_n "checking for dlfcn.h""... $ac_c" 1>&6
-echo "configure:5207: checking for dlfcn.h" >&5
+echo "configure:5175: checking for dlfcn.h" >&5
 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then
   echo $ac_n "(cached) $ac_c" 1>&6
 else
   cat > conftest.$ac_ext <<EOF
-#line 5212 "configure"
+#line 5180 "configure"
 #include "confdefs.h"
 #include <dlfcn.h>
 EOF
 ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out"
-{ (eval echo configure:5217: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
+{ (eval echo configure:5185: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
 ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"`
 if test -z "$ac_err"; then
   rm -rf conftest*
   eval "ac_cv_header_$ac_safe=yes"
 else
   echo "$ac_err" >&5
   echo "configure: failed program was:" >&5
   cat conftest.$ac_ext >&5
@@ -5241,23 +5209,23 @@ fi
     ;;
 esac
 
 
 
 
 if test $ac_cv_prog_gcc = yes; then
     echo $ac_n "checking whether ${CC-cc} needs -traditional""... $ac_c" 1>&6
-echo "configure:5250: checking whether ${CC-cc} needs -traditional" >&5
+echo "configure:5218: checking whether ${CC-cc} needs -traditional" >&5
 if eval "test \"`echo '$''{'ac_cv_prog_gcc_traditional'+set}'`\" = set"; then
   echo $ac_n "(cached) $ac_c" 1>&6
 else
     ac_pattern="Autoconf.*'x'"
   cat > conftest.$ac_ext <<EOF
-#line 5256 "configure"
+#line 5224 "configure"
 #include "confdefs.h"
 #include <sgtty.h>
 Autoconf TIOCGETP
 EOF
 if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
   egrep "$ac_pattern" >/dev/null 2>&1; then
   rm -rf conftest*
   ac_cv_prog_gcc_traditional=yes
@@ -5265,17 +5233,17 @@ else
   rm -rf conftest*
   ac_cv_prog_gcc_traditional=no
 fi
 rm -f conftest*
 
 
   if test $ac_cv_prog_gcc_traditional = no; then
     cat > conftest.$ac_ext <<EOF
-#line 5274 "configure"
+#line 5242 "configure"
 #include "confdefs.h"
 #include <termio.h>
 Autoconf TCGETA
 EOF
 if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
   egrep "$ac_pattern" >/dev/null 2>&1; then
   rm -rf conftest*
   ac_cv_prog_gcc_traditional=yes
@@ -5289,22 +5257,22 @@ echo "$ac_t""$ac_cv_prog_gcc_traditional
   if test $ac_cv_prog_gcc_traditional = yes; then
     CC="$CC -traditional"
   fi
 fi
 
 for ac_func in lchown strerror
 do
 echo $ac_n "checking for $ac_func""... $ac_c" 1>&6
-echo "configure:5298: checking for $ac_func" >&5
+echo "configure:5266: checking for $ac_func" >&5
 if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then
   echo $ac_n "(cached) $ac_c" 1>&6
 else
   cat > conftest.$ac_ext <<EOF
-#line 5303 "configure"
+#line 5271 "configure"
 #include "confdefs.h"
 /* System header to define __stub macros and hopefully few prototypes,
     which can conflict with char $ac_func(); below.  */
 #include <assert.h>
 /* Override any gcc2 internal prototype to avoid an error.  */
 /* We use char because int might match the return type of a gcc2
     builtin and then its argument prototype would still apply.  */
 char $ac_func();
@@ -5317,17 +5285,17 @@ int main() {
 #if defined (__stub_$ac_func) || defined (__stub___$ac_func)
 choke me
 #else
 $ac_func();
 #endif
 
 ; return 0; }
 EOF
-if { (eval echo configure:5326: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then
+if { (eval echo configure:5294: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then
   rm -rf conftest*
   eval "ac_cv_func_$ac_func=yes"
 else
   echo "configure: failed program was:" >&5
   cat conftest.$ac_ext >&5
   rm -rf conftest*
   eval "ac_cv_func_$ac_func=no"
 fi
@@ -5358,17 +5326,17 @@ if test "${enable_strip+set}" = set; the
 fi
 
 
 case "${target_os}" in
 hpux*)
 if test -z "$GNU_CC"; then
 
     echo $ac_n "checking for +Olit support""... $ac_c" 1>&6
-echo "configure:5367: checking for +Olit support" >&5
+echo "configure:5335: checking for +Olit support" >&5
 if eval "test \"`echo '$''{'ac_cv_hpux_usable_olit_option'+set}'`\" = set"; then
   echo $ac_n "(cached) $ac_c" 1>&6
 else
                   ac_cv_hpux_usable_olit_option=no
         rm -f conftest*
         echo 'int main() { return 0; }' | cat > conftest.c
         ${CC-cc} ${CFLAGS} +Olit=all -o conftest conftest.c > conftest.out 2>&1
         if test $? -eq 0; then
@@ -5397,17 +5365,17 @@ esac
 
 case "$target_os" in
 darwin*)
     _HAVE_PTHREADS=1
     ;;
 *)
     
 echo $ac_n "checking for pthread_create in -lpthreads""... $ac_c" 1>&6
-echo "configure:5406: checking for pthread_create in -lpthreads" >&5
+echo "configure:5374: checking for pthread_create in -lpthreads" >&5
 echo "
     #include <pthread.h> 
     void *foo(void *v) { return v; } 
     int main() { 
         pthread_t t;
         if (!pthread_create(&t, 0, &foo, 0)) {
             pthread_join(t, 0);
         }
@@ -5419,17 +5387,17 @@ echo "
     rm -f dummy.c dummy${ac_exeext} ;
     if test "$_res" = "0"; then
         echo "$ac_t""yes" 1>&6
         _HAVE_PTHREADS=1 _PTHREAD_LDFLAGS="-lpthreads"
     else
         echo "$ac_t""no" 1>&6
         
 echo $ac_n "checking for pthread_create in -lpthread""... $ac_c" 1>&6
-echo "configure:5428: checking for pthread_create in -lpthread" >&5
+echo "configure:5396: checking for pthread_create in -lpthread" >&5
 echo "
     #include <pthread.h> 
     void *foo(void *v) { return v; } 
     int main() { 
         pthread_t t;
         if (!pthread_create(&t, 0, &foo, 0)) {
             pthread_join(t, 0);
         }
@@ -5441,17 +5409,17 @@ echo "
     rm -f dummy.c dummy${ac_exeext} ;
     if test "$_res" = "0"; then
         echo "$ac_t""yes" 1>&6
         _HAVE_PTHREADS=1 _PTHREAD_LDFLAGS="-lpthread"
     else
         echo "$ac_t""no" 1>&6
         
 echo $ac_n "checking for pthread_create in -lc_r""... $ac_c" 1>&6
-echo "configure:5450: checking for pthread_create in -lc_r" >&5
+echo "configure:5418: checking for pthread_create in -lc_r" >&5
 echo "
     #include <pthread.h> 
     void *foo(void *v) { return v; } 
     int main() { 
         pthread_t t;
         if (!pthread_create(&t, 0, &foo, 0)) {
             pthread_join(t, 0);
         }
@@ -5463,17 +5431,17 @@ echo "
     rm -f dummy.c dummy${ac_exeext} ;
     if test "$_res" = "0"; then
         echo "$ac_t""yes" 1>&6
         _HAVE_PTHREADS=1 _PTHREAD_LDFLAGS="-lc_r"
     else
         echo "$ac_t""no" 1>&6
         
 echo $ac_n "checking for pthread_create in -lc""... $ac_c" 1>&6
-echo "configure:5472: checking for pthread_create in -lc" >&5
+echo "configure:5440: checking for pthread_create in -lc" >&5
 echo "
     #include <pthread.h> 
     void *foo(void *v) { return v; } 
     int main() { 
         pthread_t t;
         if (!pthread_create(&t, 0, &foo, 0)) {
             pthread_join(t, 0);
         }
@@ -5595,17 +5563,17 @@ EOF
     fi
 fi
 
 
 if test -n "$USE_PTHREADS"; then
       rm -f conftest*
    ac_cv_have_dash_pthread=no
    echo $ac_n "checking whether ${CC-cc} accepts -pthread""... $ac_c" 1>&6
-echo "configure:5604: checking whether ${CC-cc} accepts -pthread" >&5
+echo "configure:5572: checking whether ${CC-cc} accepts -pthread" >&5
    echo 'int main() { return 0; }' | cat > conftest.c
    ${CC-cc} -pthread -o conftest conftest.c > conftest.out 2>&1
    if test $? -eq 0; then
 	if test -z "`egrep -i '(unrecognize|unknown)' conftest.out | grep pthread`" && test -z "`egrep -i '(error|incorrect)' conftest.out`" ; then
 	    ac_cv_have_dash_pthread=yes
 		case "$target_os" in
 	    freebsd*)
 # Freebsd doesn't use -pthread for compiles, it uses them for linking
@@ -5618,17 +5586,17 @@ echo "configure:5604: checking whether $
 	fi
     fi
     rm -f conftest*
     echo "$ac_t""$ac_cv_have_dash_pthread" 1>&6
 
 			    ac_cv_have_dash_pthreads=no
     if test "$ac_cv_have_dash_pthread" = "no"; then
 	    echo $ac_n "checking whether ${CC-cc} accepts -pthreads""... $ac_c" 1>&6
-echo "configure:5627: checking whether ${CC-cc} accepts -pthreads" >&5
+echo "configure:5595: checking whether ${CC-cc} accepts -pthreads" >&5
     	echo 'int main() { return 0; }' | cat > conftest.c
 	    ${CC-cc} -pthreads -o conftest conftest.c > conftest.out 2>&1
     	if test $? -eq 0; then
 	    	if test -z "`egrep -i '(unrecognize|unknown)' conftest.out | grep pthreads`" && test -z "`egrep -i '(error|incorrect)' conftest.out`" ; then
 			    ac_cv_have_dash_pthreads=yes
 			    CFLAGS="$CFLAGS -pthreads"
 			    CXXFLAGS="$CXXFLAGS -pthreads"
 		    fi
--- a/nsprpub/configure.in
+++ b/nsprpub/configure.in
@@ -1008,17 +1008,17 @@ case "$target" in