author | Sebastian Hengst <archaeopteryx@coole-files.de> |
Wed, 20 Sep 2017 11:48:02 +0200 | |
changeset 431381 | a20de99fa3c1ba6287fe47d493a859a4e95120b0 |
parent 431374 | c0769d228dd3ba666d6e9b02896bebef7e996ad5 (current diff) |
parent 431380 | 46c0aa7327b3a5035e8678def3e2d216c4fb634a (diff) |
child 431382 | 4bfb0b8fb6b1da31cb6c22b243bb071b6db01984 |
child 431408 | 6d8d80beb8c82d1617b9fe939fe6035df3044738 |
child 431423 | 0c49ebf4195ce51072b24aacf01eaaffdcff9be6 |
child 431481 | 5db1536c77f3d7d9eb6e3d9f512abe95259f6748 |
push id | 7782 |
push user | ryanvm@gmail.com |
push date | Wed, 20 Sep 2017 11:51:24 +0000 |
treeherder | mozilla-beta@4bfb0b8fb6b1 [default view] [failures only] |
perfherder | [talos] [build metrics] [platform microbench] (compared to previous push) |
reviewers | merge, merge |
milestone | 57.0a1 |
first release with | nightly linux64
a20de99fa3c1
/
57.0a1
/
20170920100426
/
files
nightly mac
a20de99fa3c1
/
57.0a1
/
20170920100426
/
files
nightly win32
a20de99fa3c1
/
57.0a1
/
20170920100426
/
files
nightly win64
a20de99fa3c1
/
57.0a1
/
20170920100426
/
files
nightly linux32
|
last release without | nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
|
releases | nightly linux64
57.0a1
/
20170920100426
/
pushlog to previous
nightly mac
57.0a1
/
20170920100426
/
pushlog to previous
nightly win32
57.0a1
/
20170920100426
/
pushlog to previous
nightly win64
57.0a1
/
20170920100426
/
pushlog to previous
|
layout/generic/nsFrame.cpp | file | annotate | diff | comparison | revisions | |
layout/generic/nsIFrame.h | file | annotate | diff | comparison | revisions | |
layout/painting/nsDisplayList.cpp | file | annotate | diff | comparison | revisions | |
layout/svg/nsSVGEffects.cpp | file | annotate | diff | comparison | revisions | |
layout/svg/nsSVGEffects.h | file | annotate | diff | comparison | revisions |
--- a/accessible/base/nsAccessibilityService.cpp +++ b/accessible/base/nsAccessibilityService.cpp @@ -1302,19 +1302,21 @@ nsAccessibilityService::Init() MOZ_ASSERT(contentChild); // If we were instantiated by the chrome process, GetMsaaID() will return // a non-zero value and we may safely continue with initialization. if (!contentChild->GetMsaaID()) { // Since we were not instantiated by chrome, we need to synchronously // obtain a MSAA content process id. contentChild->SendGetA11yContentId(); } + + gApplicationAccessible = new ApplicationAccessibleWrap(); +#else + gApplicationAccessible = new ApplicationAccessible(); #endif // defined(XP_WIN) - - gApplicationAccessible = new ApplicationAccessible(); } NS_ADDREF(gApplicationAccessible); // will release in Shutdown() gApplicationAccessible->Init(); #ifdef MOZ_CRASHREPORTER CrashReporter:: AnnotateCrashReport(NS_LITERAL_CSTRING("Accessibility"),
--- a/browser/components/extensions/ExtensionPopups.jsm +++ b/browser/components/extensions/ExtensionPopups.jsm @@ -464,16 +464,17 @@ class ViewPopup extends BasePopup { * @returns {Promise<boolean>} * Resolves when the browser is ready. Resolves to `false` if the * browser was destroyed before it was fully loaded, and the popup * should be closed, or `true` otherwise. */ async attach(viewNode) { this.viewNode = viewNode; this.viewNode.addEventListener(this.DESTROY_EVENT, this); + this.viewNode.setAttribute("closemenu", "none"); if (this.extension.remote) { this.panel.setAttribute("remote", "true"); } // Wait until the browser element is fully initialized, and give it at least // a short grace period to finish loading its initial content, if necessary. //
--- a/browser/components/preferences/in-content/main.js +++ b/browser/components/preferences/in-content/main.js @@ -102,16 +102,20 @@ if (AppConstants.E10S_TESTING_ONLY) { "resource://gre/modules/UpdateUtils.jsm"); } if (AppConstants.MOZ_DEV_EDITION) { XPCOMUtils.defineLazyModuleGetter(this, "fxAccounts", "resource://gre/modules/FxAccounts.jsm"); } +// A promise that resolves when the list of application handlers is loaded. +// We store this in a global so tests can await it. +var promiseLoadHandlersList; + var gMainPane = { // The set of types the app knows how to handle. A hash of HandlerInfoWrapper // objects, indexed by type. _handledTypes: {}, // The list of types we can show, sorted by the sort column/direction. // An array of HandlerInfoWrapper objects. We build this list when we first // load the data and then rebuild it when users change a pref that affects @@ -438,21 +442,28 @@ var gMainPane = { document.getElementById("typeColumn").removeAttribute("sortDirection"); } else { this._sortColumn = document.getElementById("typeColumn"); } // Load the data and build the list of handlers. // By doing this after pageshow, we ensure it doesn't delay painting // of the preferences page. - window.addEventListener("pageshow", () => { - this._loadData(); - this._rebuildVisibleTypes(); - this._sortVisibleTypes(); - this._rebuildView(); + promiseLoadHandlersList = new Promise((resolve, reject) => { + window.addEventListener("pageshow", async () => { + try { + this._loadData(); + await this._rebuildVisibleTypes(); + this._sortVisibleTypes(); + this._rebuildView(); + resolve(); + } catch (ex) { + reject(ex); + } + }, {once: true}); }); let browserBundle = document.getElementById("browserBundle"); appendSearchKeywords("browserContainersSettings", [ browserBundle.getString("userContextPersonal.label"), browserBundle.getString("userContextWork.label"), browserBundle.getString("userContextBanking.label"), browserBundle.getString("userContextShopping.label"), @@ -1386,30 +1397,30 @@ var gMainPane = { return this; throw Cr.NS_ERROR_NO_INTERFACE; }, // nsIObserver - observe(aSubject, aTopic, aData) { + async observe(aSubject, aTopic, aData) { if (aTopic == "nsPref:changed") { if (aData == PREF_CONTAINERS_EXTENSION) { this.readBrowserContainersCheckbox(); return; } // Rebuild the list when there are changes to preferences that influence // whether or not to show certain entries in the list. if (!this._storingAction) { // These two prefs alter the list of visible types, so we have to rebuild // that list when they change. if (aData == PREF_SHOW_PLUGINS_IN_LIST || aData == PREF_HIDE_PLUGINS_WITHOUT_EXTENSIONS) { - this._rebuildVisibleTypes(); + await this._rebuildVisibleTypes(); this._sortVisibleTypes(); } // All the prefs we observe can affect what we display, so we rebuild // the view when any of them changes. this._rebuildView(); } if (AppConstants.MOZ_UPDATER) { @@ -1519,27 +1530,32 @@ var gMainPane = { handlerInfoWrapper.handledOnlyByPlugin = false; } }, // View Construction - _rebuildVisibleTypes() { + async _rebuildVisibleTypes() { // Reset the list of visible types and the visible type description counts. this._visibleTypes = []; this._visibleTypeDescriptionCount = {}; // Get the preferences that help determine what types to show. var showPlugins = this._prefSvc.getBoolPref(PREF_SHOW_PLUGINS_IN_LIST); var hidePluginsWithoutExtensions = this._prefSvc.getBoolPref(PREF_HIDE_PLUGINS_WITHOUT_EXTENSIONS); for (let type in this._handledTypes) { + // Yield before processing each handler info object to avoid monopolizing + // the main thread, as the objects are retrieved lazily, and retrieval + // can be expensive on Windows. + await new Promise(resolve => Services.tm.dispatchToMainThread(resolve)); + let handlerInfo = this._handledTypes[type]; // Hide plugins without associated extensions if so prefed so we don't // show a whole bunch of obscure types handled by plugins on Mac. // Note: though protocol types don't have extensions, we still show them; // the pref is only meant to be applied to MIME types, since plugins are // only associated with MIME types. // FIXME: should we also check the "suffixes" property of the plugin?
--- a/browser/components/preferences/in-content/tests/browser_applications_selection.js +++ b/browser/components/preferences/in-content/tests/browser_applications_selection.js @@ -3,16 +3,19 @@ var feedItem; var container; SimpleTest.requestCompleteLog(); add_task(async function setup() { await openPreferencesViaOpenPreferencesAPI("general", { leaveOpen: true }); info("Preferences page opened on the general pane."); + await gBrowser.selectedBrowser.contentWindow.promiseLoadHandlersList; + info("Apps list loaded."); + registerCleanupFunction(() => { gBrowser.removeCurrentTab(); }); }); add_task(async function getFeedItem() { win = gBrowser.selectedBrowser.contentWindow;
--- a/browser/components/preferences/in-content/tests/browser_bug410900.js +++ b/browser/components/preferences/in-content/tests/browser_bug410900.js @@ -17,19 +17,19 @@ function test() { getService(Ci.nsIExternalProtocolService); var info = extps.getProtocolHandlerInfo("apppanetest"); info.possibleApplicationHandlers.appendElement(handler); var hserv = Cc["@mozilla.org/uriloader/handler-service;1"]. getService(Ci.nsIHandlerService); hserv.store(info); - openPreferencesViaOpenPreferencesAPI("general", {leaveOpen: true}).then( - () => runTest(gBrowser.selectedBrowser.contentWindow) - ); + openPreferencesViaOpenPreferencesAPI("general", {leaveOpen: true}) + .then(() => gBrowser.selectedBrowser.contentWindow.promiseLoadHandlersList) + .then(() => runTest(gBrowser.selectedBrowser.contentWindow)); } function runTest(win) { var rbox = win.document.getElementById("handlersView"); ok(rbox, "handlersView is present"); var items = rbox && rbox.getElementsByTagName("richlistitem"); ok(items && items.length > 0, "App handler list populated");
--- a/dom/animation/KeyframeEffectReadOnly.cpp +++ b/dom/animation/KeyframeEffectReadOnly.cpp @@ -901,18 +901,16 @@ KeyframeEffectReadOnly::ConstructKeyfram aSource.mEffectOptions); // Copy cumulative change hint. mCumulativeChangeHint should be the same as // the source one because both of targets are the same. effect->mCumulativeChangeHint = aSource.mCumulativeChangeHint; // Copy aSource's keyframes and animation properties. // Note: We don't call SetKeyframes directly, which might revise the // computed offsets and rebuild the animation properties. - // FIXME: Bug 1314537: We have to make sure SharedKeyframeList is handled - // properly. effect->mKeyframes = aSource.mKeyframes; effect->mProperties = aSource.mProperties; return effect.forget(); } template<typename StyleType> nsTArray<AnimationProperty> KeyframeEffectReadOnly::BuildProperties(StyleType* aStyle)
--- a/dom/base/nsImageLoadingContent.cpp +++ b/dom/base/nsImageLoadingContent.cpp @@ -34,17 +34,17 @@ #include "nsIStreamListener.h" #include "nsIFrame.h" #include "nsIDOMNode.h" #include "nsContentUtils.h" #include "nsLayoutUtils.h" #include "nsIContentPolicy.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "gfxPrefs.h" #include "mozAutoDocUpdate.h" #include "mozilla/AsyncEventDispatcher.h" #include "mozilla/AutoRestore.h" #include "mozilla/EventStateManager.h" #include "mozilla/EventStates.h" @@ -251,17 +251,17 @@ nsImageLoadingContent::OnLoadComplete(im FireEvent(NS_LITERAL_STRING("loadend")); } } else { FireEvent(NS_LITERAL_STRING("error")); FireEvent(NS_LITERAL_STRING("loadend")); } nsCOMPtr<nsINode> thisNode = do_QueryInterface(static_cast<nsIImageLoadingContent*>(this)); - nsSVGEffects::InvalidateDirectRenderingObservers(thisNode->AsElement()); + SVGObserverUtils::InvalidateDirectRenderingObservers(thisNode->AsElement()); return NS_OK; } static bool ImageIsAnimated(imgIRequest* aRequest) { if (!aRequest) {
--- a/dom/base/test/mochitest.ini +++ b/dom/base/test/mochitest.ini @@ -618,18 +618,18 @@ skip-if = toolkit == 'android' [test_bug1295852.html] [test_bug1307730.html] [test_bug1308069.html] [test_bug1314032.html] [test_bug1318303.html] [test_bug1375050.html] [test_bug1381710.html] [test_bug1384658.html] +skip-if = toolkit == 'android' [test_bug1399605.html] -skip-if = toolkit == 'android' [test_caretPositionFromPoint.html] [test_change_policy.html] [test_clearTimeoutIntervalNoArg.html] [test_constructor-assignment.html] [test_constructor.html] [test_copyimage.html] subsuite = clipboard skip-if = toolkit == 'android' #bug 904183
--- a/dom/canvas/CanvasRenderingContext2D.cpp +++ b/dom/canvas/CanvasRenderingContext2D.cpp @@ -12,17 +12,17 @@ #include "nsIServiceManager.h" #include "nsMathUtils.h" #include "SVGImageContext.h" #include "nsContentUtils.h" #include "nsIDocument.h" #include "mozilla/dom/HTMLCanvasElement.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsPresContext.h" #include "nsIPresShell.h" #include "nsIInterfaceRequestorUtils.h" #include "nsIFrame.h" #include "nsError.h" #include "nsCSSParser.h" @@ -1295,17 +1295,17 @@ CanvasRenderingContext2D::Redraw() mIsEntireFrameInvalid = true; if (!mCanvasElement) { NS_ASSERTION(mDocShell, "Redraw with no canvas element or docshell!"); return NS_OK; } - nsSVGEffects::InvalidateDirectRenderingObservers(mCanvasElement); + SVGObserverUtils::InvalidateDirectRenderingObservers(mCanvasElement); mCanvasElement->InvalidateCanvasContent(nullptr); return NS_OK; } void CanvasRenderingContext2D::Redraw(const gfx::Rect& aR) @@ -1324,17 +1324,17 @@ CanvasRenderingContext2D::Redraw(const g return; } if (!mCanvasElement) { NS_ASSERTION(mDocShell, "Redraw with no canvas element or docshell!"); return; } - nsSVGEffects::InvalidateDirectRenderingObservers(mCanvasElement); + SVGObserverUtils::InvalidateDirectRenderingObservers(mCanvasElement); mCanvasElement->InvalidateCanvasContent(&aR); } void CanvasRenderingContext2D::DidRefresh() { if (IsTargetValid() && mIsSkiaGL) {
--- a/dom/canvas/CanvasRenderingContext2D.h +++ b/dom/canvas/CanvasRenderingContext2D.h @@ -22,17 +22,17 @@ #include "mozilla/gfx/Rect.h" #include "mozilla/gfx/2D.h" #include "mozilla/UniquePtr.h" #include "gfx2DGlue.h" #include "imgIEncoder.h" #include "nsLayoutUtils.h" #include "mozilla/EnumeratedArray.h" #include "FilterSupport.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "Layers.h" #include "nsBidi.h" class nsGlobalWindow; class nsXULElement; namespace mozilla { namespace gl {
--- a/dom/canvas/WebGLContext.cpp +++ b/dom/canvas/WebGLContext.cpp @@ -40,17 +40,17 @@ #include "nsIConsoleService.h" #include "nsIDOMEvent.h" #include "nsIGfxInfo.h" #include "nsIObserverService.h" #include "nsIVariant.h" #include "nsIWidget.h" #include "nsIXPConnect.h" #include "nsServiceManagerUtils.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "prenv.h" #include "ScopedGLHelpers.h" #include "VRManagerChild.h" #include "mozilla/layers/TextureClientSharedSurface.h" // Local #include "CanvasUtils.h" #include "WebGL1Context.h" @@ -311,17 +311,17 @@ WebGLContext::Invalidate() if (!mCanvasElement) return; mCapturedFrameInvalidated = true; if (mInvalidated) return; - nsSVGEffects::InvalidateDirectRenderingObservers(mCanvasElement); + SVGObserverUtils::InvalidateDirectRenderingObservers(mCanvasElement); mInvalidated = true; mCanvasElement->InvalidateCanvasContent(nullptr); } void WebGLContext::OnVisibilityChange() {
--- a/dom/locales/en-US/chrome/dom/dom.properties +++ b/dom/locales/en-US/chrome/dom/dom.properties @@ -327,20 +327,20 @@ URLCreateObjectURL_MediaStreamWarning=UR # LOCALIZATION NOTE: Do not translate MozAutoGainControl or autoGainControl. MozAutoGainControlWarning=mozAutoGainControl is deprecated. Use autoGainControl instead. # LOCALIZATION NOTE: Do not translate mozNoiseSuppression or noiseSuppression. MozNoiseSuppressionWarning=mozNoiseSuppression is deprecated. Use noiseSuppression instead. # LOCALIZATION NOTE: Do not translate xml:base. XMLBaseAttributeWarning=Use of xml:base attribute is deprecated and will be removed soon. Please remove any use of it. # LOCALIZATION NOTE: Do not translate "content", "Window", and "window.top" WindowContentUntrustedWarning=The ‘content’ attribute of Window objects is deprecated. Please use ‘window.top’ instead. -# LOCALIZATION NOTE: %S is the tag name of the element that starts the loop -SVGReferenceLoopWarning=There is an SVG <%S> reference loop in this document, which will prevent the document rendering correctly. -# LOCALIZATION NOTE: %S is the tag name of the element that starts the chain -SVGReferenceChainLengthExceededWarning=There is an SVG <%S> reference chain which is too long in this document, which will prevent the document rendering correctly. +# LOCALIZATION NOTE: The first %S is the tag name of the element that starts the loop, the second %S is the element's ID. +SVGReferenceLoopWarning=The SVG <%S> with ID “%S” has a reference loop. +# LOCALIZATION NOTE: The first %S is the tag name of the element in the chain where the chain was broken, the second %S is the element's ID. +SVGReferenceChainLengthExceededWarning=An SVG <%S> reference chain which is too long was abandoned at the element with ID “%S”. # LOCALIZATION NOTE: Do not translate "<script>". ScriptSourceEmpty=‘%S’ attribute of <script> element is empty. # LOCALIZATION NOTE: Do not translate "<script>". ScriptSourceInvalidUri=‘%S’ attribute of <script> element is not a valid URI: “%S” # LOCALIZATION NOTE: Do not translate "<script>". ScriptSourceLoadFailed=Loading failed for the <script> with source “%S”. # LOCALIZATION NOTE: Do not translate "<script>". ScriptSourceMalformed=<script> source URI is malformed: “%S”.
--- a/dom/media/VideoFrameContainer.cpp +++ b/dom/media/VideoFrameContainer.cpp @@ -6,17 +6,17 @@ #include "VideoFrameContainer.h" #include "mozilla/dom/HTMLMediaElement.h" #include "mozilla/Telemetry.h" #include "nsIFrame.h" #include "nsDisplayList.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" using namespace mozilla::layers; namespace mozilla { static LazyLogModule gVideoFrameContainerLog("VideoFrameContainer"); #define CONTAINER_LOG(type, msg) MOZ_LOG(gVideoFrameContainerLog, type, msg) #define NS_DispatchToMainThread(...) CompileError_UseAbstractMainThreadInstead @@ -384,14 +384,14 @@ void VideoFrameContainer::InvalidateWith if (invalidateFrame) { frame->InvalidateFrame(); } else { frame->InvalidateLayer(DisplayItemType::TYPE_VIDEO, nullptr, nullptr, asyncInvalidate ? nsIFrame::UPDATE_IS_ASYNC : 0); } } - nsSVGEffects::InvalidateDirectRenderingObservers(mElement); + SVGObserverUtils::InvalidateDirectRenderingObservers(mElement); } } // namespace mozilla #undef NS_DispatchToMainThread
--- a/dom/svg/SVGTextContentElement.cpp +++ b/dom/svg/SVGTextContentElement.cpp @@ -140,17 +140,17 @@ SVGTextContentElement::SelectSubString(u return; rv = textFrame->SelectSubString(this, charnum, nchars); } float SVGTextContentElement::GetSubStringLength(uint32_t charnum, uint32_t nchars, ErrorResult& rv) { - SVGTextFrame* textFrame = GetSVGTextFrame(); + SVGTextFrame* textFrame = GetSVGTextFrameForNonLayoutDependentQuery(); if (!textFrame) return 0.0f; float length = 0.0f; rv = textFrame->GetSubStringLength(this, charnum, nchars, &length); return length; }
--- a/dom/svg/SVGUseElement.cpp +++ b/dom/svg/SVGUseElement.cpp @@ -12,17 +12,17 @@ #include "nsGkAtoms.h" #include "mozilla/dom/SVGSVGElement.h" #include "nsIDocument.h" #include "nsIPresShell.h" #include "mozilla/dom/Element.h" #include "nsContentUtils.h" #include "nsIURI.h" #include "mozilla/URLExtraData.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGUseFrame.h" NS_IMPL_NS_NEW_NAMESPACED_SVG_ELEMENT(Use) namespace mozilla { namespace dom { JSObject* @@ -370,17 +370,17 @@ SVGUseElement::LookupHref() if (href.IsEmpty()) { return; } nsCOMPtr<nsIURI> originURI = mOriginal ? mOriginal->GetBaseURI() : GetBaseURI(); nsCOMPtr<nsIURI> baseURI = nsContentUtils::IsLocalRefURL(href) - ? nsSVGEffects::GetBaseURLForLocalRef(this, originURI) + ? SVGObserverUtils::GetBaseURLForLocalRef(this, originURI) : originURI; nsCOMPtr<nsIURI> targetURI; nsContentUtils::NewURIWithDocumentCharset(getter_AddRefs(targetURI), href, GetComposedDoc(), baseURI); mSource.Reset(this, targetURI); }
--- a/dom/svg/test/test_text_scaled.html +++ b/dom/svg/test/test_text_scaled.html @@ -22,16 +22,24 @@ SimpleTest.waitForExplicitFinish(); function runTest() { var doc = $("svg").contentWindow.document; var text1 = doc.getElementById("text1"); var text2 = doc.getElementById("text2"); var charWidth = text1.getSubStringLength(0, 1); + if (navigator.userAgent.indexOf("Linux") > -1 && charWidth == 241) { + // Workaround for a slight difference in 'charWidth' (i.e. the width of + // the 'a' char) on Linux build machines after bug 1342951. The issue + // doesn't reproduce locally on Ubuntu 17.04 so is particularly tricky to + // debug. + charWidth = 240; + } + var epsilon = 0.001; function isClose(a, b, str) { ok(Math.abs(a - b) < epsilon, str + " - " + b + " should be close to " + a); } function isPoint(pt1, x, y, str)
--- a/dom/xul/nsXULPopupListener.cpp +++ b/dom/xul/nsXULPopupListener.cpp @@ -133,18 +133,23 @@ nsXULPopupListener::HandleEvent(nsIDOMEv return NS_ERROR_FAILURE; } } nsCOMPtr<nsIContent> targetContent = do_QueryInterface(target); if (!targetContent) { return NS_OK; } - if (EventStateManager::IsRemoteTarget(targetContent)) { - return NS_OK; + + { + EventTarget* originalTarget = mouseEvent->AsEvent()->InternalDOMEvent()->GetOriginalTarget(); + nsCOMPtr<nsIContent> content = do_QueryInterface(originalTarget); + if (content && EventStateManager::IsRemoteTarget(content)) { + return NS_OK; + } } bool preventDefault; mouseEvent->AsEvent()->GetDefaultPrevented(&preventDefault); if (preventDefault && targetNode && mIsContext) { // Someone called preventDefault on a context menu. // Let's make sure they are allowed to do so. bool eventEnabled =
--- a/extensions/auth/moz.build +++ b/extensions/auth/moz.build @@ -19,13 +19,17 @@ if CONFIG['OS_ARCH'] == 'WINNT': 'nsAuthSSPI.cpp', ] DEFINES['USE_SSPI'] = True else: UNIFIED_SOURCES += [ 'nsAuthSambaNTLM.cpp', ] +LOCAL_INCLUDES += [ + '/netwerk/dns', # For nsDNSService2.h +] + FINAL_LIBRARY = 'xul' with Files('**'): BUG_COMPONENT = ('Core', 'Networking')
--- a/extensions/auth/nsAuthSSPI.cpp +++ b/extensions/auth/nsAuthSSPI.cpp @@ -9,16 +9,17 @@ // Described by IETF Internet draft: draft-brezak-kerberos-http-00.txt // (formerly draft-brezak-spnego-http-04.txt) // // Also described here: // http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnsecure/html/http-sso-1.asp // #include "nsAuthSSPI.h" +#include "nsDNSService2.h" #include "nsIServiceManager.h" #include "nsIDNSService.h" #include "nsIDNSRecord.h" #include "nsNetCID.h" #include "nsCOMPtr.h" #include "nsICryptoHash.h" #include "mozilla/Telemetry.h" @@ -87,48 +88,50 @@ InitSSPI() return NS_ERROR_UNEXPECTED; } return NS_OK; } //----------------------------------------------------------------------------- -static nsresult -MakeSN(const char *principal, nsCString &result) +nsresult +nsAuthSSPI::MakeSN(const char *principal, nsCString &result) { nsresult rv; nsAutoCString buf(principal); // The service name looks like "protocol@hostname", we need to map // this to a value that SSPI expects. To be consistent with IE, we // need to map '@' to '/' and canonicalize the hostname. int32_t index = buf.FindChar('@'); if (index == kNotFound) return NS_ERROR_UNEXPECTED; - nsCOMPtr<nsIDNSService> dns = do_GetService(NS_DNSSERVICE_CONTRACTID, &rv); + nsCOMPtr<nsIDNSService> dnsService = do_GetService(NS_DNSSERVICE_CONTRACTID, &rv); if (NS_FAILED(rv)) return rv; + auto dns = static_cast<nsDNSService*>(dnsService.get()); + // This could be expensive if our DNS cache cannot satisfy the request. // However, we should have at least hit the OS resolver once prior to // reaching this code, so provided the OS resolver has this information // cached, we should not have to worry about blocking on this function call // for very long. NOTE: because we ask for the canonical hostname, we // might end up requiring extra network activity in cases where the OS // resolver might not have enough information to satisfy the request from // its cache. This is not an issue in versions of Windows up to WinXP. nsCOMPtr<nsIDNSRecord> record; mozilla::OriginAttributes attrs; - rv = dns->ResolveNative(Substring(buf, index + 1), - nsIDNSService::RESOLVE_CANONICAL_NAME, - attrs, - getter_AddRefs(record)); + rv = dns->DeprecatedSyncResolve(Substring(buf, index + 1), + nsIDNSService::RESOLVE_CANONICAL_NAME, + attrs, + getter_AddRefs(record)); if (NS_FAILED(rv)) return rv; nsAutoCString cname; rv = record->GetCanonicalName(cname); if (NS_SUCCEEDED(rv)) { result = StringHead(buf, index) + NS_LITERAL_CSTRING("/") + cname; LOG(("Using SPN of [%s]\n", result.get()));
--- a/extensions/auth/nsAuthSSPI.h +++ b/extensions/auth/nsAuthSSPI.h @@ -37,16 +37,18 @@ public: private: ~nsAuthSSPI(); void Reset(); typedef TimeStamp MS_TimeStamp; private: + nsresult MakeSN(const char *principal, nsCString &result); + CredHandle mCred; CtxtHandle mCtxt; nsCString mServiceName; uint32_t mServiceFlags; uint32_t mMaxTokenLen; pType mPackage; nsString mDomain; nsString mUsername;
--- a/image/SVGDocumentWrapper.cpp +++ b/image/SVGDocumentWrapper.cpp @@ -20,17 +20,17 @@ #include "nsIRequest.h" #include "nsIStreamListener.h" #include "nsIXMLContentSink.h" #include "nsNetCID.h" #include "nsComponentManagerUtils.h" #include "nsSMILAnimationController.h" #include "nsServiceManagerUtils.h" #include "mozilla/dom/SVGSVGElement.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "mozilla/dom/SVGAnimatedLength.h" #include "nsMimeTypes.h" #include "DOMSVGLength.h" #include "nsDocument.h" #include "mozilla/dom/ImageTracker.h" // undef the GetCurrentTime macro defined in WinBase.h from the MS Platform SDK #undef GetCurrentTime @@ -271,17 +271,17 @@ NS_IMETHODIMP SVGDocumentWrapper::Observe(nsISupports* aSubject, const char* aTopic, const char16_t* aData) { if (!strcmp(aTopic, NS_XPCOM_SHUTDOWN_OBSERVER_ID)) { // Sever ties from rendering observers to helper-doc's root SVG node SVGSVGElement* svgElem = GetRootSVGElem(); if (svgElem) { - nsSVGEffects::RemoveAllRenderingObservers(svgElem); + SVGObserverUtils::RemoveAllRenderingObservers(svgElem); } // Clean up at XPCOM shutdown time. DestroyViewer(); if (mListener) { mListener = nullptr; } if (mLoadGroup) {
--- a/image/VectorImage.cpp +++ b/image/VectorImage.cpp @@ -19,17 +19,17 @@ #include "nsIDOMEvent.h" #include "nsIPresShell.h" #include "nsIStreamListener.h" #include "nsMimeTypes.h" #include "nsPresContext.h" #include "nsRect.h" #include "nsString.h" #include "nsStubDocumentObserver.h" -#include "nsSVGEffects.h" // for nsSVGRenderingObserver +#include "SVGObserverUtils.h" // for nsSVGRenderingObserver #include "nsWindowSizes.h" #include "ImageRegion.h" #include "ISurfaceProvider.h" #include "LookupResult.h" #include "Orientation.h" #include "SVGDocumentWrapper.h" #include "SVGDrawingParameters.h" #include "nsIDOMEventListener.h" @@ -61,17 +61,17 @@ public: { MOZ_ASSERT(mDocWrapper, "Need a non-null SVG document wrapper"); MOZ_ASSERT(mVectorImage, "Need a non-null VectorImage"); StartListening(); Element* elem = GetTarget(); MOZ_ASSERT(elem, "no root SVG node for us to observe"); - nsSVGEffects::AddRenderingObserver(elem, this); + SVGObserverUtils::AddRenderingObserver(elem, this); mInObserverList = true; } void ResumeHonoringInvalidations() { mHonoringInvalidations = true; } @@ -103,17 +103,17 @@ protected: mHonoringInvalidations = false; mVectorImage->InvalidateObserversOnNextRefreshDriverTick(); } // Our caller might've removed us from rendering-observer list. // Add ourselves back! if (!mInObserverList) { - nsSVGEffects::AddRenderingObserver(elem, this); + SVGObserverUtils::AddRenderingObserver(elem, this); mInObserverList = true; } } // Private data const RefPtr<SVGDocumentWrapper> mDocWrapper; VectorImage* const mVectorImage; // Raw pointer because it owns me. bool mHonoringInvalidations;
--- a/image/moz.build +++ b/image/moz.build @@ -96,17 +96,17 @@ include('/ipc/chromium/chromium-config.m FINAL_LIBRARY = 'xul' LOCAL_INCLUDES += [ # Because SVGDocumentWrapper.cpp includes "mozilla/dom/SVGSVGElement.h" '/dom/base', '/dom/svg', # We need to instantiate the decoders '/image/decoders', - # Because VectorImage.cpp includes nsSVGUtils.h and nsSVGEffects.h + # Because VectorImage.cpp includes nsSVGUtils.h and SVGObserverUtils.h '/layout/svg', # For URI-related functionality '/netwerk/base', # DecodePool uses thread-related facilities. '/xpcom/threads', ] # Because imgFrame.cpp includes "cairo.h"
--- a/layout/base/GeckoRestyleManager.cpp +++ b/layout/base/GeckoRestyleManager.cpp @@ -23,17 +23,17 @@ #include "GeckoProfiler.h" #include "nsAutoPtr.h" #include "nsStyleChangeList.h" #include "nsRuleProcessorData.h" #include "nsStyleContextInlines.h" #include "nsStyleSet.h" #include "nsStyleUtil.h" #include "nsCSSFrameConstructor.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsCSSPseudoElements.h" #include "nsCSSRendering.h" #include "nsAnimationManager.h" #include "nsTransitionManager.h" #include "nsViewManager.h" #include "nsSVGIntegrationUtils.h" #include "nsCSSAnonBoxes.h" #include "nsContainerFrame.h"
--- a/layout/base/PresShell.cpp +++ b/layout/base/PresShell.cpp @@ -105,17 +105,17 @@ #include "nsIObjectFrame.h" #include "nsIObjectLoadingContent.h" #include "nsNetUtil.h" #include "nsThreadUtils.h" #include "nsStyleSheetService.h" #include "gfxUtils.h" #include "nsSMILAnimationController.h" #include "SVGContentUtils.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "SVGFragmentIdentifier.h" #include "nsFrameSelection.h" #include "mozilla/dom/Performance.h" #include "nsRefreshDriver.h" #include "nsDOMNavigationTiming.h" // Drag & Drop, Clipboard @@ -9303,17 +9303,17 @@ PresShell::DoReflow(nsIFrame* target, bo tp->Accumulate(); tp->reflowCount++; timeStart = TimeStamp::Now(); } target->SchedulePaint(); nsIFrame *parent = nsLayoutUtils::GetCrossDocParentFrame(target); while (parent) { - nsSVGEffects::InvalidateDirectRenderingObservers(parent); + SVGObserverUtils::InvalidateDirectRenderingObservers(parent); parent = nsLayoutUtils::GetCrossDocParentFrame(parent); } nsIURI* uri = mDocument->GetDocumentURI(); nsCString uriString = uri ? uri->GetSpecOrDefault() : NS_LITERAL_CSTRING("N/A"); AUTO_PROFILER_LABEL_DYNAMIC("PresShell::DoReflow", GRAPHICS, uriString.get()); nsDocShell* docShell = static_cast<nsDocShell*>(GetPresContext()->GetDocShell());
--- a/layout/base/RestyleManager.cpp +++ b/layout/base/RestyleManager.cpp @@ -1549,24 +1549,24 @@ RestyleManager::ProcessRestyledFrames(ns // specify nsChangeHint_UpdateTransformLayer but don't have any // transform style, we just drop the unneeded hint here. hint &= ~nsChangeHint_UpdateTransformLayer; } if (hint & nsChangeHint_UpdateEffects) { for (nsIFrame* cont = frame; cont; cont = nsLayoutUtils::GetNextContinuationOrIBSplitSibling(cont)) { - nsSVGEffects::UpdateEffects(cont); + SVGObserverUtils::UpdateEffects(cont); } } if ((hint & nsChangeHint_InvalidateRenderingObservers) || ((hint & nsChangeHint_UpdateOpacityLayer) && frame->IsFrameOfType(nsIFrame::eSVG) && !(frame->GetStateBits() & NS_STATE_IS_OUTER_SVG))) { - nsSVGEffects::InvalidateRenderingObservers(frame); + SVGObserverUtils::InvalidateRenderingObservers(frame); } if (hint & nsChangeHint_NeedReflow) { StyleChangeReflow(frame, hint); didReflowThisFrame = true; } if ((hint & nsChangeHint_UpdateUsesOpacity) && frame->IsFrameOfType(nsIFrame::eTablePart)) {
--- a/layout/base/nsChangeHint.h +++ b/layout/base/nsChangeHint.h @@ -49,18 +49,18 @@ enum nsChangeHint : uint32_t { // The currently shown mouse cursor needs to be updated nsChangeHint_UpdateCursor = 1 << 6, /** * Used when the computed value (a URI) of one or more of an element's * filter/mask/clip/etc CSS properties changes, causing the element's frame * to start/stop referencing (or reference different) SVG resource elements. * (_Not_ used to handle changes to referenced resource elements.) Using this - * hint results in nsSVGEffects::UpdateEffects being called on the element's - * frame. + * hint results in SVGObserverUtils::UpdateEffects being called on the + * element's frame. */ nsChangeHint_UpdateEffects = 1 << 7, /** * Visual change only, but the change can be handled entirely by * updating the layer(s) for the frame. * Updates all descendants (including following placeholders to out-of-flows). */
--- a/layout/forms/nsTextControlFrame.cpp +++ b/layout/forms/nsTextControlFrame.cpp @@ -312,17 +312,17 @@ nsTextControlFrame::EnsureEditorInitiali return NS_OK; } nsresult nsTextControlFrame::CreateAnonymousContent(nsTArray<ContentInfo>& aElements) { NS_ASSERTION(mContent, "We should have a content!"); - mState |= NS_FRAME_INDEPENDENT_SELECTION; + AddStateBits(NS_FRAME_INDEPENDENT_SELECTION); nsCOMPtr<nsITextControlElement> txtCtrl = do_QueryInterface(GetContent()); NS_ASSERTION(txtCtrl, "Content not a text control element"); // Bind the frame to its text control nsresult rv = txtCtrl->BindToFrame(this); NS_ENSURE_SUCCESS(rv, rv);
--- a/layout/generic/ViewportFrame.cpp +++ b/layout/generic/ViewportFrame.cpp @@ -43,17 +43,17 @@ ViewportFrame::Init(nsIContent* aC nsContainerFrame::Init(aContent, aParent, aPrevInFlow); // No need to call CreateView() here - the frame ctor will call SetView() // with the ViewManager's root view, so we'll assign it in SetViewInternal(). nsIFrame* parent = nsLayoutUtils::GetCrossDocParentFrame(this); if (parent) { nsFrameState state = parent->GetStateBits(); - mState |= state & (NS_FRAME_IN_POPUP); + AddStateBits(state & (NS_FRAME_IN_POPUP)); } } void ViewportFrame::BuildDisplayList(nsDisplayListBuilder* aBuilder, const nsDisplayListSet& aLists) { AUTO_PROFILER_LABEL("ViewportFrame::BuildDisplayList", GRAPHICS);
--- a/layout/generic/nsBlockFrame.cpp +++ b/layout/generic/nsBlockFrame.cpp @@ -1224,17 +1224,17 @@ nsBlockFrame::Reflow(nsPresContext* reflowInput->mCBReflowInput->IsIResize() && reflowInput->mStyleText->mTextIndent.HasPercent() && !mLines.empty()) { mLines.front()->MarkDirty(); } LazyMarkLinesDirty(); - mState &= ~NS_FRAME_FIRST_REFLOW; + RemoveStateBits(NS_FRAME_FIRST_REFLOW); // Now reflow... ReflowDirtyLines(state); // If we have a next-in-flow, and that next-in-flow has pushed floats from // this frame from a previous iteration of reflow, then we should not return // a status with IsFullyComplete() equals to true, since we actually have // overflow, it's just already been handled. @@ -5263,16 +5263,24 @@ nsBlockFrame::AppendFrames(ChildListID nsFrame::ListTag(stdout, aFrameList); if (lastKid) { printf(" after "); nsFrame::ListTag(stdout, lastKid); } printf("\n"); #endif + if (nsSVGUtils::IsInSVGTextSubtree(this)) { + MOZ_ASSERT(GetParent()->IsSVGTextFrame(), + "unexpected block frame in SVG text"); + // Workaround for bug 1399425 in case this bit has been removed from the + // SVGTextFrame just before the parser adds more descendant nodes. + GetParent()->AddStateBits(NS_STATE_SVG_TEXT_CORRESPONDENCE_DIRTY); + } + AddFrames(aFrameList, lastKid); if (aListID != kNoReflowPrincipalList) { PresContext()->PresShell()-> FrameNeedsReflow(this, nsIPresShell::eTreeChange, NS_FRAME_HAS_DIRTY_CHILDREN); // XXX sufficient? } }
--- a/layout/generic/nsFrame.cpp +++ b/layout/generic/nsFrame.cpp @@ -71,17 +71,17 @@ #include "imgIContainer.h" #include "imgIRequest.h" #include "nsError.h" #include "nsContainerFrame.h" #include "nsBoxLayoutState.h" #include "nsBlockFrame.h" #include "nsDisplayList.h" #include "nsSVGIntegrationUtils.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsChangeHint.h" #include "nsDeckFrame.h" #include "nsSubDocumentFrame.h" #include "SVGTextFrame.h" #include "gfxContext.h" #include "nsAbsoluteContainingBlock.h" #include "StickyScrollContainer.h" @@ -618,46 +618,46 @@ nsFrame::Init(nsIContent* aContent if (aPrevInFlow) { mWritingMode = aPrevInFlow->GetWritingMode(); // Make sure the general flags bits are the same nsFrameState state = aPrevInFlow->GetStateBits(); // Make bits that are currently off (see constructor) the same: - mState |= state & (NS_FRAME_INDEPENDENT_SELECTION | - NS_FRAME_PART_OF_IBSPLIT | - NS_FRAME_MAY_BE_TRANSFORMED | - NS_FRAME_MAY_HAVE_GENERATED_CONTENT | - NS_FRAME_CAN_HAVE_ABSPOS_CHILDREN); + AddStateBits(state & (NS_FRAME_INDEPENDENT_SELECTION | + NS_FRAME_PART_OF_IBSPLIT | + NS_FRAME_MAY_BE_TRANSFORMED | + NS_FRAME_MAY_HAVE_GENERATED_CONTENT | + NS_FRAME_CAN_HAVE_ABSPOS_CHILDREN)); } else { PresContext()->ConstructedFrame(); } if (GetParent()) { nsFrameState state = GetParent()->GetStateBits(); // Make bits that are currently off (see constructor) the same: - mState |= state & (NS_FRAME_INDEPENDENT_SELECTION | - NS_FRAME_GENERATED_CONTENT | - NS_FRAME_IS_SVG_TEXT | - NS_FRAME_IN_POPUP | - NS_FRAME_IS_NONDISPLAY); + AddStateBits(state & (NS_FRAME_INDEPENDENT_SELECTION | + NS_FRAME_GENERATED_CONTENT | + NS_FRAME_IS_SVG_TEXT | + NS_FRAME_IN_POPUP | + NS_FRAME_IS_NONDISPLAY)); if (HasAnyStateBits(NS_FRAME_IN_POPUP) && TrackingVisibility()) { // Assume all frames in popups are visible. IncApproximateVisibleCount(); } } const nsStyleDisplay *disp = StyleDisplay(); if (disp->HasTransform(this) || (IsFrameOfType(eSupportsCSSTransforms) && nsLayoutUtils::HasAnimationOfProperty(this, eCSSProperty_transform))) { // The frame gets reconstructed if we toggle the -moz-transform // property, so we can set this bit here and then ignore it. - mState |= NS_FRAME_MAY_BE_TRANSFORMED; + AddStateBits(NS_FRAME_MAY_BE_TRANSFORMED); } if (disp->mPosition == NS_STYLE_POSITION_STICKY && !aPrevInFlow && !(mState & NS_FRAME_IS_NONDISPLAY) && !disp->IsInnerTableStyle()) { // Note that we only add first continuations, but we really only // want to add first continuation-or-ib-split-siblings. But since we // don't yet know if we're a later part of a block-in-inline split, @@ -710,17 +710,17 @@ nsFrame::DestroyFrom(nsIFrame* aDestruct "destroy called on frame while scripts not blocked"); NS_ASSERTION(!GetNextSibling() && !GetPrevSibling(), "Frames should be removed before destruction."); NS_ASSERTION(aDestructRoot, "Must specify destruct root"); MOZ_ASSERT(!HasAbsolutelyPositionedChildren()); MOZ_ASSERT(!HasAnyStateBits(NS_FRAME_PART_OF_IBSPLIT), "NS_FRAME_PART_OF_IBSPLIT set on non-nsContainerFrame?"); - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); if (StyleDisplay()->mPosition == NS_STYLE_POSITION_STICKY) { StickyScrollContainer* ssc = StickyScrollContainer::GetStickyScrollContainerForFrame(this); if (ssc) { ssc->RemoveFrame(this); } } @@ -5887,21 +5887,22 @@ nsIFrame::ComputeISizeValue(gfxContext* void nsFrame::DidReflow(nsPresContext* aPresContext, const ReflowInput* aReflowInput, nsDidReflowStatus aStatus) { NS_FRAME_TRACE_MSG(NS_FRAME_TRACE_CALLS, ("nsFrame::DidReflow: aStatus=%d", static_cast<uint32_t>(aStatus))); - nsSVGEffects::InvalidateDirectRenderingObservers(this, nsSVGEffects::INVALIDATE_REFLOW); + SVGObserverUtils::InvalidateDirectRenderingObservers(this, + SVGObserverUtils::INVALIDATE_REFLOW); if (nsDidReflowStatus::FINISHED == aStatus) { - mState &= ~(NS_FRAME_IN_REFLOW | NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | - NS_FRAME_HAS_DIRTY_CHILDREN); + RemoveStateBits(NS_FRAME_IN_REFLOW | NS_FRAME_FIRST_REFLOW | + NS_FRAME_IS_DIRTY | NS_FRAME_HAS_DIRTY_CHILDREN); } // Notify the percent bsize observer if there is a percent bsize. // The observer may be able to initiate another reflow with a computed // bsize. This happens in the case where a table cell has no computed // bsize but can fabricate one when the cell bsize is known. if (aReflowInput && aReflowInput->mPercentBSizeObserver && !GetPrevInFlow()) { @@ -6402,22 +6403,22 @@ nsIFrame::GetTransformMatrix(const nsIFr return Matrix4x4::Translation(NSAppUnitsToFloatPixels(delta.x, scaleFactor), NSAppUnitsToFloatPixels(delta.y, scaleFactor), 0.0f); } static void InvalidateRenderingObservers(nsIFrame* aDisplayRoot, nsIFrame* aFrame) { MOZ_ASSERT(aDisplayRoot == nsLayoutUtils::GetDisplayRootFrame(aFrame)); - nsSVGEffects::InvalidateDirectRenderingObservers(aFrame); + SVGObserverUtils::InvalidateDirectRenderingObservers(aFrame); nsIFrame* parent = aFrame; while (parent != aDisplayRoot && (parent = nsLayoutUtils::GetCrossDocParentFrame(parent)) && !parent->HasAnyStateBits(NS_FRAME_DESCENDANT_NEEDS_PAINT)) { - nsSVGEffects::InvalidateDirectRenderingObservers(parent); + SVGObserverUtils::InvalidateDirectRenderingObservers(parent); } } void SchedulePaintInternal(nsIFrame* aDisplayRoot, nsIFrame* aFrame, nsIFrame::PaintType aType = nsIFrame::PAINT_DEFAULT) { MOZ_ASSERT(aDisplayRoot == nsLayoutUtils::GetDisplayRootFrame(aFrame)); @@ -6446,27 +6447,27 @@ SchedulePaintInternal(nsIFrame* aDisplay } } static void InvalidateFrameInternal(nsIFrame *aFrame, bool aHasDisplayItem = true) { if (aHasDisplayItem) { aFrame->AddStateBits(NS_FRAME_NEEDS_PAINT); } - nsSVGEffects::InvalidateDirectRenderingObservers(aFrame); + SVGObserverUtils::InvalidateDirectRenderingObservers(aFrame); bool needsSchedulePaint = false; if (nsLayoutUtils::IsPopup(aFrame)) { needsSchedulePaint = true; } else { nsIFrame *parent = nsLayoutUtils::GetCrossDocParentFrame(aFrame); while (parent && !parent->HasAnyStateBits(NS_FRAME_DESCENDANT_NEEDS_PAINT)) { if (aHasDisplayItem && !parent->HasAnyStateBits(NS_FRAME_IS_NONDISPLAY)) { parent->AddStateBits(NS_FRAME_DESCENDANT_NEEDS_PAINT); } - nsSVGEffects::InvalidateDirectRenderingObservers(parent); + SVGObserverUtils::InvalidateDirectRenderingObservers(parent); // If we're inside a popup, then we need to make sure that we // call schedule paint so that the NS_FRAME_UPDATE_LAYER_TREE // flag gets added to the popup display root frame. if (nsLayoutUtils::IsPopup(parent)) { needsSchedulePaint = true; break; } @@ -6992,34 +6993,34 @@ nsFrame::UnionChildOverflow(nsOverflowAr bool nsFrame::IsFrameTreeTooDeep(const ReflowInput& aReflowInput, ReflowOutput& aMetrics, nsReflowStatus& aStatus) { if (aReflowInput.mReflowDepth > MAX_FRAME_DEPTH) { NS_WARNING("frame tree too deep; setting zero size and returning"); - mState |= NS_FRAME_TOO_DEEP_IN_FRAME_TREE; + AddStateBits(NS_FRAME_TOO_DEEP_IN_FRAME_TREE); ClearOverflowRects(); aMetrics.ClearSize(); aMetrics.SetBlockStartAscent(0); aMetrics.mCarriedOutBEndMargin.Zero(); aMetrics.mOverflowAreas.Clear(); aStatus.Reset(); if (GetNextInFlow()) { // Reflow depth might vary between reflows, so we might have // successfully reflowed and split this frame before. If so, we // shouldn't delete its continuations. aStatus.SetIncomplete(); } return true; } - mState &= ~NS_FRAME_TOO_DEEP_IN_FRAME_TREE; + RemoveStateBits(NS_FRAME_TOO_DEEP_IN_FRAME_TREE); return false; } bool nsIFrame::IsBlockWrapper() const { nsIAtom *pseudoType = StyleContext()->GetPseudo(); return (pseudoType == nsCSSAnonBoxes::mozBlockInsideInlineWrapper || @@ -9133,17 +9134,17 @@ nsIFrame::FinishAndStoreOverflow(nsOverf bool anyOverflowChanged; if (aOverflowAreas != nsOverflowAreas(bounds, bounds)) { anyOverflowChanged = SetOverflowAreas(aOverflowAreas); } else { anyOverflowChanged = ClearOverflowRects(); } if (anyOverflowChanged) { - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); } return anyOverflowChanged; } void nsIFrame::RecomputePerspectiveChildrenOverflow(const nsIFrame* aStartFrame, EffectSet* aEffectSet) {
--- a/layout/generic/nsFrameStateBits.h +++ b/layout/generic/nsFrameStateBits.h @@ -385,16 +385,20 @@ FRAME_STATE_BIT(SVG, 22, NS_STATE_SVG_PO // can be true even if a viewport size change will not affect mPositions, // determining a completley accurate value for // NS_STATE_SVG_POSITIONING_MAY_USE_PERCENTAGES would require extra work that is // probably not worth it. FRAME_STATE_BIT(SVG, 23, NS_STATE_SVG_POSITIONING_MAY_USE_PERCENTAGES) FRAME_STATE_BIT(SVG, 24, NS_STATE_SVG_TEXT_IN_REFLOW) +// Set on SVGTextFrame frames when they need a +// TextNodeCorrespondenceRecorder::RecordCorrespondence call +// to update the cached nsTextNode indexes that they correspond to. +FRAME_STATE_BIT(SVG, 25, NS_STATE_SVG_TEXT_CORRESPONDENCE_DIRTY) // == Frame state bits that apply to text frames ============================== FRAME_STATE_GROUP(Text, nsTextFrame) // -- Flags set during reflow ------------------------------------------------- // nsTextFrame.cpp defines TEXT_REFLOW_FLAGS to be all of these bits.
--- a/layout/generic/nsIFrame.h +++ b/layout/generic/nsIFrame.h @@ -4097,17 +4097,17 @@ protected: */ inline void PropagateRootElementWritingMode(mozilla::WritingMode aRootElemWM); void MarkInReflow() { #ifdef DEBUG_dbaron_off // bug 81268 NS_ASSERTION(!(mState & NS_FRAME_IN_REFLOW), "frame is already in reflow"); #endif - mState |= NS_FRAME_IN_REFLOW; + AddStateBits(NS_FRAME_IN_REFLOW); } nsFrameState mState; /** * List of properties attached to the frame. */ FrameProperties mProperties;
--- a/layout/generic/nsImageFrame.cpp +++ b/layout/generic/nsImageFrame.cpp @@ -986,25 +986,25 @@ nsImageFrame::Reflow(nsPresContext* NS_FRAME_TRACE(NS_FRAME_TRACE_CALLS, ("enter nsImageFrame::Reflow: availSize=%d,%d", aReflowInput.AvailableWidth(), aReflowInput.AvailableHeight())); NS_PRECONDITION(mState & NS_FRAME_IN_REFLOW, "frame is not in reflow"); // see if we have a frozen size (i.e. a fixed width and height) if (HaveFixedSize(aReflowInput)) { - mState |= IMAGE_SIZECONSTRAINED; + AddStateBits(IMAGE_SIZECONSTRAINED); } else { - mState &= ~IMAGE_SIZECONSTRAINED; + RemoveStateBits(IMAGE_SIZECONSTRAINED); } // XXXldb These two bits are almost exact opposites (except in the // middle of the initial reflow); remove IMAGE_GOTINITIALREFLOW. if (GetStateBits() & NS_FRAME_FIRST_REFLOW) { - mState |= IMAGE_GOTINITIALREFLOW; + AddStateBits(IMAGE_GOTINITIALREFLOW); } mComputedSize = nsSize(aReflowInput.ComputedWidth(), aReflowInput.ComputedHeight()); aMetrics.Width() = mComputedSize.width; aMetrics.Height() = mComputedSize.height;
--- a/layout/generic/nsTextFrame.cpp +++ b/layout/generic/nsTextFrame.cpp @@ -4544,17 +4544,17 @@ nsContinuingTextFrame::Init(nsIContent* MOZ_ASSERT(nextBidiData.precedingControl == kBidiLevelNone, "There shouldn't be any virtual bidi formatting character " "between continuations"); #endif nextContinuation->mContentOffset = mContentOffset; nextContinuation = nextContinuation->GetNextContinuation(); } } - mState |= NS_FRAME_IS_BIDI; + AddStateBits(NS_FRAME_IS_BIDI); } // prev frame is bidi } void nsContinuingTextFrame::DestroyFrom(nsIFrame* aDestructRoot) { ClearFrameOffsetCache(); @@ -4867,17 +4867,17 @@ nsTextFrame::CharacterDataChanged(Charac // (For subsequent frames with this same parent, we can just set their // dirty bit without bothering to call FrameNeedsReflow again.) nsIFrame* lastDirtiedFrameParent = nullptr; nsIPresShell* shell = PresContext()->GetPresShell(); do { // textFrame contained deleted text (or the insertion point, // if this was a pure insertion). - textFrame->mState &= ~TEXT_WHITESPACE_FLAGS; + textFrame->RemoveStateBits(TEXT_WHITESPACE_FLAGS); textFrame->ClearTextRuns(); nsIFrame* parentOfTextFrame = textFrame->GetParent(); bool areAncestorsAwareOfReflowRequest = false; if (lastDirtiedFrameParent == parentOfTextFrame) { // An earlier iteration of this loop already called // FrameNeedsReflow for a sibling of |textFrame|. areAncestorsAwareOfReflowRequest = true; @@ -10315,17 +10315,17 @@ nsTextFrame::IsEmpty() if (mState & TEXT_IS_ONLY_WHITESPACE) { return true; } bool isEmpty = IsAllWhitespace(mContent->GetText(), textStyle->mWhiteSpace != mozilla::StyleWhiteSpace::PreLine); - mState |= (isEmpty ? TEXT_IS_ONLY_WHITESPACE : TEXT_ISNOT_ONLY_WHITESPACE); + AddStateBits(isEmpty ? TEXT_IS_ONLY_WHITESPACE : TEXT_ISNOT_ONLY_WHITESPACE); return isEmpty; } #ifdef DEBUG_FRAME_DUMP // Translate the mapped content into a string that's printable void nsTextFrame::ToCString(nsCString& aBuf, int32_t* aTotalContentLength) const {
--- a/layout/painting/nsCSSRendering.cpp +++ b/layout/painting/nsCSSRendering.cpp @@ -41,17 +41,17 @@ #include "nsITheme.h" #include "nsThemeConstants.h" #include "nsLayoutUtils.h" #include "nsBlockFrame.h" #include "nsStyleStructInlines.h" #include "nsCSSFrameConstructor.h" #include "nsCSSProps.h" #include "nsContentUtils.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGIntegrationUtils.h" #include "gfxDrawable.h" #include "GeckoProfiler.h" #include "nsCSSRenderingBorders.h" #include "mozilla/css/ImageLoader.h" #include "ImageContainer.h" #include "mozilla/Telemetry.h" #include "gfxUtils.h"
--- a/layout/painting/nsDisplayList.cpp +++ b/layout/painting/nsDisplayList.cpp @@ -38,17 +38,17 @@ #include "nsThemeConstants.h" #include "BorderConsts.h" #include "LayerTreeInvalidation.h" #include "imgIContainer.h" #include "BasicLayers.h" #include "nsBoxFrame.h" #include "nsSubDocumentFrame.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGElement.h" #include "nsSVGClipPathFrame.h" #include "GeckoProfiler.h" #include "nsViewManager.h" #include "ImageLayers.h" #include "ImageContainer.h" #include "nsCanvasFrame.h" #include "StickyScrollContainer.h" @@ -8750,18 +8750,18 @@ ComputeMaskGeometry(PaintFramesParams& a { // Properties are added lazily and may have been removed by a restyle, so // make sure all applicable ones are set again. nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(aParams.frame); const nsStyleSVGReset *svgReset = firstFrame->StyleSVGReset(); - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(firstFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(firstFrame); nsTArray<nsSVGMaskFrame *> maskFrames = effectProperties.GetMaskFrames(); if (maskFrames.Length() == 0) { return; } gfxContext& ctx = aParams.ctx; nsIFrame* frame = aParams.frame; @@ -8871,18 +8871,18 @@ nsDisplayMask::BuildLayer(nsDisplayListB } if (mFrame->StyleEffects()->mOpacity == 0.0f && mHandleOpacity) { return nullptr; } nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(mFrame); - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(firstFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(firstFrame); if (effectProperties.HasInvalidClipPath() || effectProperties.HasInvalidMask()) { return nullptr; } RefPtr<ContainerLayer> container = aManager->GetLayerBuilder()-> BuildContainerLayerFor(aBuilder, aManager, mFrame, this, &mList, @@ -9063,18 +9063,18 @@ nsDisplayMask::CreateWebRenderCommands(m } #ifdef MOZ_DUMP_PAINTING void nsDisplayMask::PrintEffects(nsACString& aTo) { nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(mFrame); - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(firstFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(firstFrame); nsSVGClipPathFrame *clipPathFrame = effectProperties.GetClipPathFrame(); bool first = true; aTo += " effects=("; if (mFrame->StyleEffects()->mOpacity != 1.0f && mHandleOpacity) { first = false; aTo += nsPrintfCString("opacity(%f)", mFrame->StyleEffects()->mOpacity); } if (clipPathFrame) { @@ -9130,18 +9130,18 @@ nsDisplayFilter::BuildLayer(nsDisplayLis } if (mFrame->StyleEffects()->mOpacity == 0.0f && mHandleOpacity) { return nullptr; } nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(mFrame); - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(firstFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(firstFrame); if (effectProperties.HasInvalidFilter()) { return nullptr; } MOZ_ASSERT(effectProperties.mFilter && mFrame->StyleEffects()->HasFilters(), "By getting here, we must have valid CSS filters."); @@ -9295,18 +9295,18 @@ nsDisplayFilter::CreateWebRenderCommands } #ifdef MOZ_DUMP_PAINTING void nsDisplayFilter::PrintEffects(nsACString& aTo) { nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(mFrame); - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(firstFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(firstFrame); bool first = true; aTo += " effects=("; if (mFrame->StyleEffects()->mOpacity != 1.0f && mHandleOpacity) { first = false; aTo += nsPrintfCString("opacity(%f)", mFrame->StyleEffects()->mOpacity); } if (effectProperties.HasValidFilter()) { if (!first) {
--- a/layout/painting/nsImageRenderer.cpp +++ b/layout/painting/nsImageRenderer.cpp @@ -15,17 +15,17 @@ #include "ImageOps.h" #include "mozilla/layers/StackingContextHelper.h" #include "nsContentUtils.h" #include "nsCSSRendering.h" #include "nsCSSRenderingGradients.h" #include "nsIFrame.h" #include "nsStyleStructInlines.h" #include "nsSVGDisplayableFrame.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGIntegrationUtils.h" using namespace mozilla; using namespace mozilla::gfx; using namespace mozilla::image; using namespace mozilla::layers; nsSize @@ -175,19 +175,19 @@ nsImageRenderer::PrepareImage() case eStyleImageType_Element: { nsAutoString elementId = NS_LITERAL_STRING("#") + nsDependentAtomString(mImage->GetElementId()); nsCOMPtr<nsIURI> targetURI; nsCOMPtr<nsIURI> base = mForFrame->GetContent()->GetBaseURI(); nsContentUtils::NewURIWithDocumentCharset(getter_AddRefs(targetURI), elementId, mForFrame->GetContent()->GetUncomposedDoc(), base); - nsSVGPaintingProperty* property = nsSVGEffects::GetPaintingPropertyForURI( + nsSVGPaintingProperty* property = SVGObserverUtils::GetPaintingPropertyForURI( targetURI, mForFrame->FirstContinuation(), - nsSVGEffects::BackgroundImageProperty()); + SVGObserverUtils::BackgroundImageProperty()); if (!property) { mPrepareResult = DrawResult::BAD_IMAGE; return false; } // If the referenced element is an <img>, <canvas>, or <video> element, // prefer SurfaceFromElement as it's more reliable. mImageElementSurface =
--- a/layout/style/ImageLoader.cpp +++ b/layout/style/ImageLoader.cpp @@ -8,17 +8,17 @@ #include "mozilla/css/ImageLoader.h" #include "nsAutoPtr.h" #include "nsContentUtils.h" #include "nsLayoutUtils.h" #include "nsError.h" #include "nsDisplayList.h" #include "FrameLayerBuilder.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "imgIContainer.h" #include "Image.h" namespace mozilla { namespace css { void ImageLoader::DropDocumentReference() @@ -357,17 +357,17 @@ ImageLoader::DoRedraw(FrameSet* aFrameSe // might not find the right display item. frame->InvalidateFrame(); } else { FrameLayerBuilder::IterateRetainedDataFor(frame, InvalidateImagesCallback); // Update ancestor rendering observers (-moz-element etc) nsIFrame *f = frame; while (f && !f->HasAnyStateBits(NS_FRAME_DESCENDANT_NEEDS_PAINT)) { - nsSVGEffects::InvalidateDirectRenderingObservers(f); + SVGObserverUtils::InvalidateDirectRenderingObservers(f); f = nsLayoutUtils::GetCrossDocParentFrame(f); } if (aForcePaint) { frame->SchedulePaint(); } } }
--- a/layout/svg/AutoReferenceChainGuard.h +++ b/layout/svg/AutoReferenceChainGuard.h @@ -146,19 +146,21 @@ public: *mFrameInUse = true; (*mChainCounter)--; return true; } private: void ReportErrorToConsole() { - nsAutoString tag; - mFrame->GetContent()->AsElement()->GetTagName(tag); - const char16_t* params[] = { tag.get() }; + nsAutoString tag, id; + dom::Element* element = mFrame->GetContent()->AsElement(); + element->GetTagName(tag); + element->GetId(id); + const char16_t* params[] = { tag.get(), id.get() }; auto doc = mFrame->GetContent()->OwnerDoc(); auto warning = *mFrameInUse ? nsIDocument::eSVGReferenceLoop : nsIDocument::eSVGReferenceChainLengthExceeded; doc->WarnOnceAbout(warning, /* asError */ true, params, ArrayLength(params)); }
--- a/layout/svg/SVGContextPaint.cpp +++ b/layout/svg/SVGContextPaint.cpp @@ -5,17 +5,17 @@ #include "SVGContextPaint.h" #include "gfxContext.h" #include "gfxUtils.h" #include "mozilla/gfx/2D.h" #include "mozilla/Preferences.h" #include "nsIDocument.h" #include "nsSVGPaintServerFrame.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGPaintServerFrame.h" using namespace mozilla::gfx; using namespace mozilla::image; namespace mozilla { using image::imgDrawingParams; @@ -86,22 +86,22 @@ SVGContextPaint::IsAllowedForImageFromUR static void SetupInheritablePaint(const DrawTarget* aDrawTarget, const gfxMatrix& aContextMatrix, nsIFrame* aFrame, float& aOpacity, SVGContextPaint* aOuterContextPaint, SVGContextPaintImpl::Paint& aTargetPaint, nsStyleSVGPaint nsStyleSVG::*aFillOrStroke, - nsSVGEffects::PaintingPropertyDescriptor aProperty, + SVGObserverUtils::PaintingPropertyDescriptor aProperty, imgDrawingParams& aImgParams) { const nsStyleSVG *style = aFrame->StyleSVG(); nsSVGPaintServerFrame *ps = - nsSVGEffects::GetPaintServer(aFrame, aFillOrStroke, aProperty); + SVGObserverUtils::GetPaintServer(aFrame, aFillOrStroke, aProperty); if (ps) { RefPtr<gfxPattern> pattern = ps->GetPaintServerPattern(aFrame, aDrawTarget, aContextMatrix, aFillOrStroke, aOpacity, aImgParams); if (pattern) { aTargetPaint.SetPaintServer(aFrame, aContextMatrix, ps); @@ -152,34 +152,35 @@ SVGContextPaintImpl::Init(const DrawTarg SetFillOpacity(0.0f); } else { float opacity = nsSVGUtils::GetOpacity(style->FillOpacitySource(), style->mFillOpacity, aOuterContextPaint); SetupInheritablePaint(aDrawTarget, aContextMatrix, aFrame, opacity, aOuterContextPaint, mFillPaint, &nsStyleSVG::mFill, - nsSVGEffects::FillProperty(), aImgParams); + SVGObserverUtils::FillProperty(), aImgParams); SetFillOpacity(opacity); toDraw |= DrawMode::GLYPH_FILL; } // stroke: if (style->mStroke.Type() == eStyleSVGPaintType_None) { SetStrokeOpacity(0.0f); } else { float opacity = nsSVGUtils::GetOpacity(style->StrokeOpacitySource(), style->mStrokeOpacity, aOuterContextPaint); SetupInheritablePaint(aDrawTarget, aContextMatrix, aFrame, opacity, aOuterContextPaint, mStrokePaint, - &nsStyleSVG::mStroke, nsSVGEffects::StrokeProperty(), + &nsStyleSVG::mStroke, + SVGObserverUtils::StrokeProperty(), aImgParams); SetStrokeOpacity(opacity); toDraw |= DrawMode::GLYPH_STROKE; } return toDraw;
--- a/layout/svg/SVGFEContainerFrame.cpp +++ b/layout/svg/SVGFEContainerFrame.cpp @@ -3,17 +3,17 @@ * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ // Keep in (case-insensitive) order: #include "nsContainerFrame.h" #include "nsGkAtoms.h" #include "nsIFrame.h" #include "nsLiteralString.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGFilters.h" /* * This frame is used by filter primitive elements that * have special child elements that provide parameters. */ class SVGFEContainerFrame : public nsContainerFrame { @@ -84,13 +84,13 @@ nsresult SVGFEContainerFrame::AttributeChanged(int32_t aNameSpaceID, nsIAtom* aAttribute, int32_t aModType) { nsSVGFE *element = static_cast<nsSVGFE*>(GetContent()); if (element->AttributeAffectsRendering(aNameSpaceID, aAttribute)) { MOZ_ASSERT(GetParent()->IsSVGFilterFrame(), "Observers observe the filter, so that's what we must invalidate"); - nsSVGEffects::InvalidateDirectRenderingObservers(GetParent()); + SVGObserverUtils::InvalidateDirectRenderingObservers(GetParent()); } return nsContainerFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType); }
--- a/layout/svg/SVGFEImageFrame.cpp +++ b/layout/svg/SVGFEImageFrame.cpp @@ -5,17 +5,17 @@ // Keep in (case-insensitive) order: #include "nsContainerFrame.h" #include "nsContentUtils.h" #include "nsFrame.h" #include "nsGkAtoms.h" #include "nsIDOMMutationEvent.h" #include "nsLiteralString.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGFilters.h" #include "mozilla/dom/SVGFEImageElement.h" using namespace mozilla; using namespace mozilla::dom; class SVGFEImageFrame final : public nsFrame { @@ -120,17 +120,17 @@ nsresult SVGFEImageFrame::AttributeChanged(int32_t aNameSpaceID, nsIAtom* aAttribute, int32_t aModType) { SVGFEImageElement* element = static_cast<SVGFEImageElement*>(GetContent()); if (element->AttributeAffectsRendering(aNameSpaceID, aAttribute)) { MOZ_ASSERT(GetParent()->IsSVGFilterFrame(), "Observers observe the filter, so that's what we must invalidate"); - nsSVGEffects::InvalidateDirectRenderingObservers(GetParent()); + SVGObserverUtils::InvalidateDirectRenderingObservers(GetParent()); } // Currently our SMIL implementation does not modify the DOM attributes. Once // we implement the SVG 2 SMIL behaviour this can be removed // SVGFEImageElement::AfterSetAttr's implementation will be sufficient. if (aModType == nsIDOMMutationEvent::SMIL && aAttribute == nsGkAtoms::href && (aNameSpaceID == kNameSpaceID_XLink ||
--- a/layout/svg/SVGFELeafFrame.cpp +++ b/layout/svg/SVGFELeafFrame.cpp @@ -2,17 +2,17 @@ /* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ // Keep in (case-insensitive) order: #include "nsContainerFrame.h" #include "nsFrame.h" #include "nsGkAtoms.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGFilters.h" /* * This frame is used by filter primitive elements that don't * have special child elements that provide parameters. */ class SVGFELeafFrame final : public nsFrame { @@ -82,13 +82,13 @@ nsresult SVGFELeafFrame::AttributeChanged(int32_t aNameSpaceID, nsIAtom* aAttribute, int32_t aModType) { nsSVGFE *element = static_cast<nsSVGFE*>(GetContent()); if (element->AttributeAffectsRendering(aNameSpaceID, aAttribute)) { MOZ_ASSERT(GetParent()->IsSVGFilterFrame(), "Observers observe the filter, so that's what we must invalidate"); - nsSVGEffects::InvalidateDirectRenderingObservers(GetParent()); + SVGObserverUtils::InvalidateDirectRenderingObservers(GetParent()); } return nsFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType); }
--- a/layout/svg/SVGFEUnstyledLeafFrame.cpp +++ b/layout/svg/SVGFEUnstyledLeafFrame.cpp @@ -2,17 +2,17 @@ /* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ // Keep in (case-insensitive) order: #include "nsContainerFrame.h" #include "nsFrame.h" #include "nsGkAtoms.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGFilters.h" class SVGFEUnstyledLeafFrame : public nsFrame { friend nsIFrame* NS_NewSVGFEUnstyledLeafFrame(nsIPresShell* aPresShell, nsStyleContext* aContext); protected: explicit SVGFEUnstyledLeafFrame(nsStyleContext* aContext) @@ -61,13 +61,13 @@ nsresult SVGFEUnstyledLeafFrame::AttributeChanged(int32_t aNameSpaceID, nsIAtom* aAttribute, int32_t aModType) { SVGFEUnstyledElement *element = static_cast<SVGFEUnstyledElement*>(GetContent()); if (element->AttributeAffectsRendering(aNameSpaceID, aAttribute)) { MOZ_ASSERT(GetParent()->GetParent()->IsSVGFilterFrame(), "Observers observe the filter, so that's what we must invalidate"); - nsSVGEffects::InvalidateDirectRenderingObservers(GetParent()->GetParent()); + SVGObserverUtils::InvalidateDirectRenderingObservers(GetParent()->GetParent()); } return nsFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType); }
--- a/layout/svg/SVGGeometryFrame.cpp +++ b/layout/svg/SVGGeometryFrame.cpp @@ -13,17 +13,17 @@ #include "gfxUtils.h" #include "mozilla/gfx/2D.h" #include "mozilla/gfx/Helpers.h" #include "mozilla/RefPtr.h" #include "mozilla/SVGContextPaint.h" #include "nsDisplayList.h" #include "nsGkAtoms.h" #include "nsLayoutUtils.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGIntegrationUtils.h" #include "nsSVGMarkerFrame.h" #include "SVGGeometryElement.h" #include "nsSVGUtils.h" #include "mozilla/ArrayUtils.h" #include "SVGAnimatedTransformList.h" #include "SVGContentUtils.h" #include "SVGGraphicsElement.h" @@ -412,25 +412,25 @@ SVGGeometryFrame::ReflowSVG() gfxRect extent = GetBBoxContribution(Matrix(), flags).ToThebesRect(); mRect = nsLayoutUtils::RoundGfxRectToAppRect(extent, PresContext()->AppUnitsPerCSSPixel()); if (mState & NS_FRAME_FIRST_REFLOW) { // Make sure we have our filter property (if any) before calling // FinishAndStoreOverflow (subsequent filter changes are handled off // nsChangeHint_UpdateEffects): - nsSVGEffects::UpdateEffects(this); + SVGObserverUtils::UpdateEffects(this); } nsRect overflow = nsRect(nsPoint(0,0), mRect.Size()); nsOverflowAreas overflowAreas(overflow, overflow); FinishAndStoreOverflow(overflowAreas, mRect.Size()); - mState &= ~(NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | - NS_FRAME_HAS_DIRTY_CHILDREN); + RemoveStateBits(NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | + NS_FRAME_HAS_DIRTY_CHILDREN); // Invalidate, but only if this is not our first reflow (since if it is our // first reflow then we haven't had our first paint yet). if (!(GetParent()->GetStateBits() & NS_FRAME_FIRST_REFLOW)) { InvalidateFrame(); } } @@ -697,30 +697,30 @@ SVGGeometryFrame::GetCanvasTM() SVGGeometryFrame::MarkerProperties SVGGeometryFrame::GetMarkerProperties(SVGGeometryFrame *aFrame) { NS_ASSERTION(!aFrame->GetPrevContinuation(), "aFrame should be first continuation"); MarkerProperties result; nsCOMPtr<nsIURI> markerURL = - nsSVGEffects::GetMarkerURI(aFrame, &nsStyleSVG::mMarkerStart); + SVGObserverUtils::GetMarkerURI(aFrame, &nsStyleSVG::mMarkerStart); result.mMarkerStart = - nsSVGEffects::GetMarkerProperty(markerURL, aFrame, - nsSVGEffects::MarkerBeginProperty()); + SVGObserverUtils::GetMarkerProperty(markerURL, aFrame, + SVGObserverUtils::MarkerBeginProperty()); - markerURL = nsSVGEffects::GetMarkerURI(aFrame, &nsStyleSVG::mMarkerMid); + markerURL = SVGObserverUtils::GetMarkerURI(aFrame, &nsStyleSVG::mMarkerMid); result.mMarkerMid = - nsSVGEffects::GetMarkerProperty(markerURL, aFrame, - nsSVGEffects::MarkerMiddleProperty()); + SVGObserverUtils::GetMarkerProperty(markerURL, aFrame, + SVGObserverUtils::MarkerMiddleProperty()); - markerURL = nsSVGEffects::GetMarkerURI(aFrame, &nsStyleSVG::mMarkerEnd); + markerURL = SVGObserverUtils::GetMarkerURI(aFrame, &nsStyleSVG::mMarkerEnd); result.mMarkerEnd = - nsSVGEffects::GetMarkerProperty(markerURL, aFrame, - nsSVGEffects::MarkerEndProperty()); + SVGObserverUtils::GetMarkerProperty(markerURL, aFrame, + SVGObserverUtils::MarkerEndProperty()); return result; } nsSVGMarkerFrame * SVGGeometryFrame::MarkerProperties::GetMarkerStartFrame() { if (!mMarkerStart) return nullptr;
rename from layout/svg/nsSVGEffects.cpp rename to layout/svg/SVGObserverUtils.cpp --- a/layout/svg/nsSVGEffects.cpp +++ b/layout/svg/SVGObserverUtils.cpp @@ -1,15 +1,15 @@ /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ /* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ // Main header first: -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" // Keep others in (case-insensitive) order: #include "mozilla/RestyleManager.h" #include "mozilla/RestyleManagerInlines.h" #include "nsCSSFrameConstructor.h" #include "nsISupportsImpl.h" #include "nsSVGClipPathFrame.h" #include "nsSVGPaintServerFrame.h" @@ -36,17 +36,17 @@ nsSVGRenderingObserver::StartListening() void nsSVGRenderingObserver::StopListening() { Element* target = GetTarget(); if (target) { target->RemoveMutationObserver(this); if (mInObserverList) { - nsSVGEffects::RemoveRenderingObserver(target, this); + SVGObserverUtils::RemoveRenderingObserver(target, this); mInObserverList = false; } } NS_ASSERTION(!mInObserverList, "still in an observer list?"); } static nsSVGRenderingObserverList * GetObserverList(Element *aElement) @@ -64,17 +64,17 @@ nsSVGRenderingObserver::GetReferencedEle nsSVGRenderingObserverList *observerList = GetObserverList(target); bool inObserverList = observerList && observerList->Contains(this); NS_ASSERTION(inObserverList == mInObserverList, "failed to track whether we're in our referenced element's observer list!"); } else { NS_ASSERTION(!mInObserverList, "In whose observer list are we, then?"); } #endif if (target && !mInObserverList) { - nsSVGEffects::AddRenderingObserver(target, this); + SVGObserverUtils::AddRenderingObserver(target, this); mInObserverList = true; } return target; } nsIFrame* nsSVGRenderingObserver::GetReferencedFrame() { @@ -194,17 +194,17 @@ nsSVGIDRenderingObserver::~nsSVGIDRender { StopListening(); } void nsSVGIDRenderingObserver::DoUpdate() { if (mElement.get() && mInObserverList) { - nsSVGEffects::RemoveRenderingObserver(mElement.get(), this); + SVGObserverUtils::RemoveRenderingObserver(mElement.get(), this); mInObserverList = false; } } void nsSVGFrameReferenceFromProperty::Detach() { mFrame = nullptr; @@ -224,17 +224,18 @@ nsSVGFrameReferenceFromProperty::Get() NS_IMPL_ISUPPORTS(nsSVGRenderingObserverProperty, nsIMutationObserver) void nsSVGRenderingObserverProperty::DoUpdate() { nsSVGIDRenderingObserver::DoUpdate(); nsIFrame* frame = mFrameReference.Get(); - if (frame && frame->IsFrameOfType(nsIFrame::eSVG)) { + + if (frame && frame->HasAllStateBits(NS_FRAME_SVG_LAYOUT)) { // Changes should propagate out to things that might be observing // the referencing frame or its ancestors. nsLayoutUtils::PostRestyleEvent( frame->GetContent()->AsElement(), nsRestyleHint(0), nsChangeHint_InvalidateRenderingObservers); } } @@ -299,17 +300,17 @@ nsSVGFilterChainObserver::nsSVGFilterCha { for (uint32_t i = 0; i < aFilters.Length(); i++) { if (aFilters[i].GetType() != NS_STYLE_FILTER_URL) continue; // aFilteredFrame can be null if this filter belongs to a // CanvasRenderingContext2D. nsCOMPtr<nsIURI> filterURL = aFilteredFrame - ? nsSVGEffects::GetFilterURI(aFilteredFrame, i) + ? SVGObserverUtils::GetFilterURI(aFilteredFrame, i) : aFilters[i].GetURL()->ResolveLocalRef(aFilteredElement); RefPtr<nsSVGFilterReference> reference = new nsSVGFilterReference(filterURL, aFilteredElement, this); mReferences.AppendElement(reference); } } @@ -344,17 +345,19 @@ nsSVGFilterProperty::DoUpdate() nsIFrame* frame = mFrameReference.Get(); if (!frame) return; // Repaint asynchronously in case the filter frame is being torn down nsChangeHint changeHint = nsChangeHint(nsChangeHint_RepaintFrame); - if (frame && frame->IsFrameOfType(nsIFrame::eSVG)) { + // Since we don't call nsSVGRenderingObserverProperty::DoUpdate, we have to + // add this bit ourselves. + if (frame->HasAllStateBits(NS_FRAME_SVG_LAYOUT)) { // Changes should propagate out to things that might be observing // the referencing frame or its ancestors. changeHint |= nsChangeHint_InvalidateRenderingObservers; } // Don't need to request UpdateOverflow if we're being reflowed. if (!(frame->GetStateBits() & NS_FRAME_IN_REFLOW)) { changeHint |= nsChangeHint_UpdateOverflow; @@ -369,41 +372,37 @@ nsSVGMarkerProperty::DoUpdate() nsSVGRenderingObserverProperty::DoUpdate(); nsIFrame* frame = mFrameReference.Get(); if (!frame) return; NS_ASSERTION(frame->IsFrameOfType(nsIFrame::eSVG), "SVG frame expected"); - // Repaint asynchronously in case the marker frame is being torn down - nsChangeHint changeHint = - nsChangeHint(nsChangeHint_RepaintFrame); - // Don't need to request ReflowFrame if we're being reflowed. if (!(frame->GetStateBits() & NS_FRAME_IN_REFLOW)) { - changeHint |= nsChangeHint_InvalidateRenderingObservers; // XXXjwatt: We need to unify SVG into standard reflow so we can just use // nsChangeHint_NeedReflow | nsChangeHint_NeedDirtyReflow here. // XXXSDL KILL THIS!!! nsSVGUtils::ScheduleReflowSVG(frame); } frame->PresContext()->RestyleManager()->PostRestyleEvent( - frame->GetContent()->AsElement(), nsRestyleHint(0), changeHint); + frame->GetContent()->AsElement(), nsRestyleHint(0), + nsChangeHint_RepaintFrame); } NS_IMPL_ISUPPORTS(nsSVGMaskProperty, nsISupports) nsSVGMaskProperty::nsSVGMaskProperty(nsIFrame* aFrame) : mFrame(aFrame) { const nsStyleSVGReset *svgReset = aFrame->StyleSVGReset(); for (uint32_t i = 0; i < svgReset->mMask.mImageCount; i++) { - nsCOMPtr<nsIURI> maskUri = nsSVGEffects::GetMaskURI(aFrame, i); + nsCOMPtr<nsIURI> maskUri = SVGObserverUtils::GetMaskURI(aFrame, i); bool hasRef = false; if (maskUri) { maskUri->GetHasRef(&hasRef); } // Accrording to maskUri, nsSVGPaintingProperty's ctor may trigger an // external SVG resource download, so we should pass maskUri in only if // maskUri has a chance pointing to an SVG mask resource. @@ -496,52 +495,50 @@ nsSVGPaintingProperty::DoUpdate() { nsSVGRenderingObserverProperty::DoUpdate(); nsIFrame* frame = mFrameReference.Get(); if (!frame) return; if (frame->GetStateBits() & NS_FRAME_SVG_LAYOUT) { - nsLayoutUtils::PostRestyleEvent( - frame->GetContent()->AsElement(), nsRestyleHint(0), - nsChangeHint_InvalidateRenderingObservers); frame->InvalidateFrameSubtree(); } else { InvalidateAllContinuations(frame); } } static nsSVGFilterProperty* GetOrCreateFilterProperty(nsIFrame* aFrame) { const nsStyleEffects* effects = aFrame->StyleEffects(); if (!effects->HasFilters()) return nullptr; nsSVGFilterProperty *prop = - aFrame->GetProperty(nsSVGEffects::FilterProperty()); + aFrame->GetProperty(SVGObserverUtils::FilterProperty()); if (prop) return prop; prop = new nsSVGFilterProperty(effects->mFilters, aFrame); NS_ADDREF(prop); - aFrame->SetProperty(nsSVGEffects::FilterProperty(), prop); + aFrame->SetProperty(SVGObserverUtils::FilterProperty(), prop); return prop; } static nsSVGMaskProperty* GetOrCreateMaskProperty(nsIFrame* aFrame) { - nsSVGMaskProperty *prop = aFrame->GetProperty(nsSVGEffects::MaskProperty()); + nsSVGMaskProperty *prop = + aFrame->GetProperty(SVGObserverUtils::MaskProperty()); if (prop) return prop; prop = new nsSVGMaskProperty(aFrame); NS_ADDREF(prop); - aFrame->SetProperty(nsSVGEffects::MaskProperty(), prop); + aFrame->SetProperty(SVGObserverUtils::MaskProperty(), prop); return prop; } template<class T> static T* GetEffectProperty(nsIURI* aURI, nsIFrame* aFrame, const mozilla::FramePropertyDescriptor<T>* aProperty) { @@ -553,91 +550,91 @@ GetEffectProperty(nsIURI* aURI, nsIFrame return prop; prop = new T(aURI, aFrame, false); NS_ADDREF(prop); aFrame->SetProperty(aProperty, prop); return prop; } nsSVGMarkerProperty* -nsSVGEffects::GetMarkerProperty(nsIURI* aURI, nsIFrame* aFrame, +SVGObserverUtils::GetMarkerProperty(nsIURI* aURI, nsIFrame* aFrame, const mozilla::FramePropertyDescriptor<nsSVGMarkerProperty>* aProperty) { MOZ_ASSERT(aFrame->IsSVGGeometryFrame() && static_cast<SVGGeometryElement*>(aFrame->GetContent())->IsMarkable(), "Bad frame"); return GetEffectProperty(aURI, aFrame, aProperty); } nsSVGTextPathProperty* -nsSVGEffects::GetTextPathProperty(nsIURI* aURI, nsIFrame* aFrame, +SVGObserverUtils::GetTextPathProperty(nsIURI* aURI, nsIFrame* aFrame, const mozilla::FramePropertyDescriptor<nsSVGTextPathProperty>* aProperty) { return GetEffectProperty(aURI, aFrame, aProperty); } nsSVGPaintingProperty* -nsSVGEffects::GetPaintingProperty(nsIURI* aURI, nsIFrame* aFrame, +SVGObserverUtils::GetPaintingProperty(nsIURI* aURI, nsIFrame* aFrame, const mozilla::FramePropertyDescriptor<nsSVGPaintingProperty>* aProperty) { return GetEffectProperty(aURI, aFrame, aProperty); } nsSVGPaintingProperty* -nsSVGEffects::GetPaintingPropertyForURI(nsIURI* aURI, nsIFrame* aFrame, +SVGObserverUtils::GetPaintingPropertyForURI(nsIURI* aURI, nsIFrame* aFrame, URIObserverHashtablePropertyDescriptor aProperty) { if (!aURI) return nullptr; - nsSVGEffects::URIObserverHashtable *hashtable = + SVGObserverUtils::URIObserverHashtable *hashtable = aFrame->GetProperty(aProperty); if (!hashtable) { - hashtable = new nsSVGEffects::URIObserverHashtable(); + hashtable = new SVGObserverUtils::URIObserverHashtable(); aFrame->SetProperty(aProperty, hashtable); } nsSVGPaintingProperty* prop = static_cast<nsSVGPaintingProperty*>(hashtable->GetWeak(aURI)); if (!prop) { - bool watchImage = aProperty == nsSVGEffects::BackgroundImageProperty(); + bool watchImage = aProperty == SVGObserverUtils::BackgroundImageProperty(); prop = new nsSVGPaintingProperty(aURI, aFrame, watchImage); hashtable->Put(aURI, prop); } return prop; } -nsSVGEffects::EffectProperties -nsSVGEffects::GetEffectProperties(nsIFrame* aFrame) +SVGObserverUtils::EffectProperties +SVGObserverUtils::GetEffectProperties(nsIFrame* aFrame) { NS_ASSERTION(!aFrame->GetPrevContinuation(), "aFrame should be first continuation"); EffectProperties result; const nsStyleSVGReset *style = aFrame->StyleSVGReset(); result.mFilter = GetOrCreateFilterProperty(aFrame); if (style->mClipPath.GetType() == StyleShapeSourceType::URL) { - nsCOMPtr<nsIURI> pathURI = nsSVGEffects::GetClipPathURI(aFrame); + nsCOMPtr<nsIURI> pathURI = SVGObserverUtils::GetClipPathURI(aFrame); result.mClipPath = GetPaintingProperty(pathURI, aFrame, ClipPathProperty()); } else { result.mClipPath = nullptr; } MOZ_ASSERT(style->mMask.mImageCount > 0); result.mMask = style->HasMask() ? GetOrCreateMaskProperty(aFrame) : nullptr; return result; } nsSVGPaintServerFrame * -nsSVGEffects::GetPaintServer(nsIFrame* aTargetFrame, - nsStyleSVGPaint nsStyleSVG::* aPaint, - PaintingPropertyDescriptor aType) +SVGObserverUtils::GetPaintServer(nsIFrame* aTargetFrame, + nsStyleSVGPaint nsStyleSVG::* aPaint, + PaintingPropertyDescriptor aType) { const nsStyleSVG* svgStyle = aTargetFrame->StyleSVG(); if ((svgStyle->*aPaint).Type() != eStyleSVGPaintType_Server) return nullptr; // If we're looking at a frame within SVG text, then we need to look up // to find the right frame to get the painting property off. We should at // least look up past a text frame, and if the text frame's parent is the @@ -646,48 +643,49 @@ nsSVGEffects::GetPaintServer(nsIFrame* a if (frame->GetContent()->IsNodeOfType(nsINode::eTEXT)) { frame = frame->GetParent(); nsIFrame* grandparent = frame->GetParent(); if (grandparent && grandparent->IsSVGTextFrame()) { frame = grandparent; } } - nsCOMPtr<nsIURI> paintServerURL = nsSVGEffects::GetPaintURI(frame, aPaint); + nsCOMPtr<nsIURI> paintServerURL = + SVGObserverUtils::GetPaintURI(frame, aPaint); nsSVGPaintingProperty *property = - nsSVGEffects::GetPaintingProperty(paintServerURL, frame, aType); + SVGObserverUtils::GetPaintingProperty(paintServerURL, frame, aType); if (!property) return nullptr; nsIFrame* result = property->GetReferencedFrame(); if (!result) return nullptr; LayoutFrameType type = result->Type(); if (type != LayoutFrameType::SVGLinearGradient && type != LayoutFrameType::SVGRadialGradient && type != LayoutFrameType::SVGPattern) return nullptr; return static_cast<nsSVGPaintServerFrame*>(result); } nsSVGClipPathFrame * -nsSVGEffects::EffectProperties::GetClipPathFrame() +SVGObserverUtils::EffectProperties::GetClipPathFrame() { if (!mClipPath) return nullptr; nsSVGClipPathFrame* frame = static_cast<nsSVGClipPathFrame*>( mClipPath->GetReferencedFrame(LayoutFrameType::SVGClipPath, nullptr)); return frame; } nsTArray<nsSVGMaskFrame *> -nsSVGEffects::EffectProperties::GetMaskFrames() +SVGObserverUtils::EffectProperties::GetMaskFrames() { nsTArray<nsSVGMaskFrame *> result; if (!mMask) return result; bool ok = true; const nsTArray<RefPtr<nsSVGPaintingProperty>>& props = mMask->GetProps(); for (size_t i = 0; i < props.Length(); i++) { @@ -705,55 +703,55 @@ nsSVGEffects::EffectProperties::GetMaskF } result.AppendElement(maskFrame); } return result; } bool -nsSVGEffects::EffectProperties::HasNoOrValidEffects() +SVGObserverUtils::EffectProperties::HasNoOrValidEffects() { return HasNoOrValidClipPath() && HasNoOrValidMask() && HasNoOrValidFilter(); } bool -nsSVGEffects::EffectProperties::HasNoOrValidClipPath() +SVGObserverUtils::EffectProperties::HasNoOrValidClipPath() { if (mClipPath) { bool ok = true; nsSVGClipPathFrame* frame = static_cast<nsSVGClipPathFrame*>( mClipPath->GetReferencedFrame(LayoutFrameType::SVGClipPath, &ok)); if (!ok || (frame && !frame->IsValid())) { return false; } } return true; } bool -nsSVGEffects::EffectProperties::HasNoOrValidMask() +SVGObserverUtils::EffectProperties::HasNoOrValidMask() { if (mMask) { bool ok = true; const nsTArray<RefPtr<nsSVGPaintingProperty>>& props = mMask->GetProps(); for (size_t i = 0; i < props.Length(); i++) { props[i]->GetReferencedFrame(LayoutFrameType::SVGMask, &ok); if (!ok) { return false; } } } return true; } void -nsSVGEffects::UpdateEffects(nsIFrame* aFrame) +SVGObserverUtils::UpdateEffects(nsIFrame* aFrame) { NS_ASSERTION(aFrame->GetContent()->IsElement(), "aFrame's content should be an element"); aFrame->DeleteProperty(FilterProperty()); aFrame->DeleteProperty(MaskProperty()); aFrame->DeleteProperty(ClipPathProperty()); aFrame->DeleteProperty(MarkerBeginProperty()); @@ -776,17 +774,17 @@ nsSVGEffects::UpdateEffects(nsIFrame* aF markerURL = GetMarkerURI(aFrame, &nsStyleSVG::mMarkerMid); GetMarkerProperty(markerURL, aFrame, MarkerMiddleProperty()); markerURL = GetMarkerURI(aFrame, &nsStyleSVG::mMarkerEnd); GetMarkerProperty(markerURL, aFrame, MarkerEndProperty()); } } nsSVGFilterProperty* -nsSVGEffects::GetFilterProperty(nsIFrame* aFrame) +SVGObserverUtils::GetFilterProperty(nsIFrame* aFrame) { NS_ASSERTION(!aFrame->GetPrevContinuation(), "aFrame should be first continuation"); if (!aFrame->StyleEffects()->HasFilters()) return nullptr; return aFrame->GetProperty(FilterProperty()); } @@ -843,58 +841,58 @@ nsSVGRenderingObserverList::RemoveAll() // Our list is now cleared. We need to notify the observers we've removed, // so they can update their state & remove themselves as mutation-observers. for (uint32_t i = 0; i < observers.Length(); ++i) { observers[i]->NotifyEvictedFromRenderingObserverList(); } } void -nsSVGEffects::AddRenderingObserver(Element* aElement, - nsSVGRenderingObserver* aObserver) +SVGObserverUtils::AddRenderingObserver(Element* aElement, + nsSVGRenderingObserver* aObserver) { nsSVGRenderingObserverList *observerList = GetObserverList(aElement); if (!observerList) { observerList = new nsSVGRenderingObserverList(); if (!observerList) return; aElement->SetProperty(nsGkAtoms::renderingobserverlist, observerList, nsINode::DeleteProperty<nsSVGRenderingObserverList>); } aElement->SetHasRenderingObservers(true); observerList->Add(aObserver); } void -nsSVGEffects::RemoveRenderingObserver(Element* aElement, - nsSVGRenderingObserver* aObserver) +SVGObserverUtils::RemoveRenderingObserver(Element* aElement, + nsSVGRenderingObserver* aObserver) { nsSVGRenderingObserverList *observerList = GetObserverList(aElement); if (observerList) { NS_ASSERTION(observerList->Contains(aObserver), "removing observer from an element we're not observing?"); observerList->Remove(aObserver); if (observerList->IsEmpty()) { aElement->SetHasRenderingObservers(false); } } } void -nsSVGEffects::RemoveAllRenderingObservers(Element* aElement) +SVGObserverUtils::RemoveAllRenderingObservers(Element* aElement) { nsSVGRenderingObserverList *observerList = GetObserverList(aElement); if (observerList) { observerList->RemoveAll(); aElement->SetHasRenderingObservers(false); } } void -nsSVGEffects::InvalidateRenderingObservers(nsIFrame* aFrame) +SVGObserverUtils::InvalidateRenderingObservers(nsIFrame* aFrame) { NS_ASSERTION(!aFrame->GetPrevContinuation(), "aFrame must be first continuation"); nsIContent* content = aFrame->GetContent(); if (!content || !content->IsElement()) return; // If the rendering has changed, the bounds may well have changed too: @@ -917,17 +915,18 @@ nsSVGEffects::InvalidateRenderingObserve observerList->InvalidateAll(); return; } } } } void -nsSVGEffects::InvalidateDirectRenderingObservers(Element* aElement, uint32_t aFlags /* = 0 */) +SVGObserverUtils::InvalidateDirectRenderingObservers(Element* aElement, + uint32_t aFlags /* = 0 */) { nsIFrame* frame = aElement->GetPrimaryFrame(); if (frame) { // If the rendering has changed, the bounds may well have changed too: frame->DeleteProperty(nsSVGUtils::ObjectBoundingBoxProperty()); } if (aElement->HasRenderingObservers()) { @@ -938,26 +937,27 @@ nsSVGEffects::InvalidateDirectRenderingO } else { observerList->InvalidateAll(); } } } } void -nsSVGEffects::InvalidateDirectRenderingObservers(nsIFrame* aFrame, uint32_t aFlags /* = 0 */) +SVGObserverUtils::InvalidateDirectRenderingObservers(nsIFrame* aFrame, + uint32_t aFlags /* = 0 */) { nsIContent* content = aFrame->GetContent(); if (content && content->IsElement()) { InvalidateDirectRenderingObservers(content->AsElement(), aFlags); } } already_AddRefed<nsIURI> -nsSVGEffects::GetBaseURLForLocalRef(nsIContent* content, nsIURI* aDocURI) +SVGObserverUtils::GetBaseURLForLocalRef(nsIContent* content, nsIURI* aDocURI) { MOZ_ASSERT(content); // For a local-reference URL, resolve that fragment against the current // document that relative URLs are resolved against. nsCOMPtr<nsIURI> baseURI = content->OwnerDoc()->GetDocumentURI(); if (content->IsInAnonymousSubtree()) { @@ -1009,71 +1009,72 @@ ResolveURLUsingLocalRef(nsIFrame* aFrame // Non-local-reference URL. if (!aURL->IsLocalRef()) { nsCOMPtr<nsIURI> result = aURL->GetURI(); return result.forget(); } nsCOMPtr<nsIURI> baseURI = - nsSVGEffects::GetBaseURLForLocalRef(aFrame->GetContent(), aURL->GetURI()); + SVGObserverUtils::GetBaseURLForLocalRef(aFrame->GetContent(), + aURL->GetURI()); return aURL->ResolveLocalRef(baseURI); } already_AddRefed<nsIURI> -nsSVGEffects::GetMarkerURI(nsIFrame* aFrame, - RefPtr<css::URLValue> nsStyleSVG::* aMarker) +SVGObserverUtils::GetMarkerURI(nsIFrame* aFrame, + RefPtr<css::URLValue> nsStyleSVG::* aMarker) { return ResolveURLUsingLocalRef(aFrame, aFrame->StyleSVG()->*aMarker); } already_AddRefed<nsIURI> -nsSVGEffects::GetClipPathURI(nsIFrame* aFrame) +SVGObserverUtils::GetClipPathURI(nsIFrame* aFrame) { const nsStyleSVGReset* svgResetStyle = aFrame->StyleSVGReset(); MOZ_ASSERT(svgResetStyle->mClipPath.GetType() == StyleShapeSourceType::URL); css::URLValue* url = svgResetStyle->mClipPath.GetURL(); return ResolveURLUsingLocalRef(aFrame, url); } already_AddRefed<nsIURI> -nsSVGEffects::GetFilterURI(nsIFrame* aFrame, uint32_t aIndex) +SVGObserverUtils::GetFilterURI(nsIFrame* aFrame, uint32_t aIndex) { const nsStyleEffects* effects = aFrame->StyleEffects(); MOZ_ASSERT(effects->mFilters.Length() > aIndex); MOZ_ASSERT(effects->mFilters[aIndex].GetType() == NS_STYLE_FILTER_URL); return ResolveURLUsingLocalRef(aFrame, effects->mFilters[aIndex].GetURL()); } already_AddRefed<nsIURI> -nsSVGEffects::GetFilterURI(nsIFrame* aFrame, const nsStyleFilter& aFilter) +SVGObserverUtils::GetFilterURI(nsIFrame* aFrame, const nsStyleFilter& aFilter) { MOZ_ASSERT(aFrame->StyleEffects()->mFilters.Length()); MOZ_ASSERT(aFilter.GetType() == NS_STYLE_FILTER_URL); return ResolveURLUsingLocalRef(aFrame, aFilter.GetURL()); } already_AddRefed<nsIURI> -nsSVGEffects::GetPaintURI(nsIFrame* aFrame, - nsStyleSVGPaint nsStyleSVG::* aPaint) +SVGObserverUtils::GetPaintURI(nsIFrame* aFrame, + nsStyleSVGPaint nsStyleSVG::* aPaint) { const nsStyleSVG* svgStyle = aFrame->StyleSVG(); MOZ_ASSERT((svgStyle->*aPaint).Type() == nsStyleSVGPaintType::eStyleSVGPaintType_Server); return ResolveURLUsingLocalRef(aFrame, (svgStyle->*aPaint).GetPaintServer()); } already_AddRefed<nsIURI> -nsSVGEffects::GetMaskURI(nsIFrame* aFrame, uint32_t aIndex) +SVGObserverUtils::GetMaskURI(nsIFrame* aFrame, uint32_t aIndex) { const nsStyleSVGReset* svgReset = aFrame->StyleSVGReset(); MOZ_ASSERT(svgReset->mMask.mLayers.Length() > aIndex); mozilla::css::URLValueData* data = svgReset->mMask.mLayers[aIndex].mImage.GetURLValue(); return ResolveURLUsingLocalRef(aFrame, data); }
rename from layout/svg/nsSVGEffects.h rename to layout/svg/SVGObserverUtils.h --- a/layout/svg/nsSVGEffects.h +++ b/layout/svg/SVGObserverUtils.h @@ -421,17 +421,17 @@ public: * to them. */ void RemoveAll(); private: nsTHashtable<nsPtrHashKey<nsSVGRenderingObserver> > mObservers; }; -class nsSVGEffects +class SVGObserverUtils { public: typedef mozilla::dom::Element Element; typedef nsInterfaceHashtable<nsURIHashKey, nsIMutationObserver> URIObserverHashtable; using PaintingPropertyDescriptor = const mozilla::FramePropertyDescriptor<nsSVGPaintingProperty>*;
--- a/layout/svg/SVGTextFrame.cpp +++ b/layout/svg/SVGTextFrame.cpp @@ -22,17 +22,17 @@ #include "nsBidiPresUtils.h" #include "nsBlockFrame.h" #include "nsCaret.h" #include "nsContentUtils.h" #include "nsGkAtoms.h" #include "nsIDOMSVGLength.h" #include "nsISelection.h" #include "nsQuickSort.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGOuterSVGFrame.h" #include "nsSVGPaintServerFrame.h" #include "mozilla/dom/SVGRect.h" #include "nsSVGIntegrationUtils.h" #include "nsSVGUtils.h" #include "nsTArray.h" #include "nsTextFrame.h" #include "nsTextNode.h" @@ -1387,18 +1387,23 @@ private: * The index into the current nsTextNode's character content. */ uint32_t mNodeCharIndex; }; /* static */ void TextNodeCorrespondenceRecorder::RecordCorrespondence(SVGTextFrame* aRoot) { - TextNodeCorrespondenceRecorder recorder(aRoot); - recorder.Record(aRoot); + if (aRoot->GetStateBits() & NS_STATE_SVG_TEXT_CORRESPONDENCE_DIRTY) { + // Resolve bidi so that continuation frames are created if necessary: + aRoot->MaybeResolveBidiForAnonymousBlockChild(); + TextNodeCorrespondenceRecorder recorder(aRoot); + recorder.Record(aRoot); + aRoot->RemoveStateBits(NS_STATE_SVG_TEXT_CORRESPONDENCE_DIRTY); + } } void TextNodeCorrespondenceRecorder::Record(SVGTextFrame* aRoot) { if (!mNodeIterator.Current()) { // If there are no nsTextNodes then there is nothing to do. return; @@ -1723,19 +1728,19 @@ private: * The iterator's current position relative to mSubtree. */ SubtreePosition mSubtreePosition; }; uint32_t TextFrameIterator::UndisplayedCharacters() const { - MOZ_ASSERT(!(mRootFrame->PrincipalChildList().FirstChild() && - NS_SUBTREE_DIRTY(mRootFrame->PrincipalChildList().FirstChild())), - "should have already reflowed the anonymous block child"); + MOZ_ASSERT(!(mRootFrame->GetStateBits() & + NS_STATE_SVG_TEXT_CORRESPONDENCE_DIRTY), + "Text correspondence must be up to date"); if (!mCurrentFrame) { return mRootFrame->mTrailingUndisplayedCharacters; } nsTextFrame* frame = do_QueryFrame(mCurrentFrame); return GetUndisplayedCharactersBeforeFrame(frame); } @@ -2426,17 +2431,17 @@ private: bool mPostReflow; }; CharIterator::CharIterator(SVGTextFrame* aSVGTextFrame, CharIterator::CharacterFilter aFilter, nsIContent* aSubtree, bool aPostReflow) : mFilter(aFilter), - mFrameIterator(FrameIfAnonymousChildReflowed(aSVGTextFrame), aSubtree), + mFrameIterator(aSVGTextFrame, aSubtree), mFrameForTrimCheck(nullptr), mTrimmedOffset(0), mTrimmedLength(0), mTextElementCharIndex(0), mGlyphStartTextElementCharIndex(0), mLengthAdjustScaleFactor(aSVGTextFrame->mLengthAdjustScaleFactor) , mPostReflow(aPostReflow) { @@ -3402,17 +3407,17 @@ SVGTextFrame::HandleAttributeChangeInDes NotifyGlyphMetricsChange(); } else if ((aNameSpaceID == kNameSpaceID_XLink || aNameSpaceID == kNameSpaceID_None) && aAttribute == nsGkAtoms::href) { // Blow away our reference, if any nsIFrame* childElementFrame = aElement->GetPrimaryFrame(); if (childElementFrame) { childElementFrame->DeleteProperty( - nsSVGEffects::HrefAsTextPathProperty()); + SVGObserverUtils::HrefAsTextPathProperty()); NotifyGlyphMetricsChange(); } } } else { if (aNameSpaceID == kNameSpaceID_None && IsGlyphPositioningAttribute(aAttribute)) { NotifyGlyphMetricsChange(); } @@ -3774,17 +3779,19 @@ SVGTextFrame::ReflowSVG() { NS_ASSERTION(nsSVGUtils::OuterSVGIsCallingReflowSVG(this), "This call is probaby a wasteful mistake"); MOZ_ASSERT(!(GetStateBits() & NS_FRAME_IS_NONDISPLAY), "ReflowSVG mechanism not designed for this"); if (!nsSVGUtils::NeedsReflowSVG(this)) { - NS_ASSERTION(!(mState & NS_STATE_SVG_POSITIONING_DIRTY), "How did this happen?"); + MOZ_ASSERT(!HasAnyStateBits(NS_STATE_SVG_TEXT_CORRESPONDENCE_DIRTY | + NS_STATE_SVG_POSITIONING_DIRTY), + "How did this happen?"); return; } MaybeReflowAnonymousBlockChild(); UpdateGlyphPositioning(); nsPresContext* presContext = PresContext(); @@ -3830,24 +3837,24 @@ SVGTextFrame::ReflowSVG() // covered region. mRect.Inflate(presContext->AppUnitsPerDevPixel()); } if (mState & NS_FRAME_FIRST_REFLOW) { // Make sure we have our filter property (if any) before calling // FinishAndStoreOverflow (subsequent filter changes are handled off // nsChangeHint_UpdateEffects): - nsSVGEffects::UpdateEffects(this); + SVGObserverUtils::UpdateEffects(this); } // Now unset the various reflow bits. Do this before calling // FinishAndStoreOverflow since FinishAndStoreOverflow can require glyph // positions (to resolve transform-origin). - mState &= ~(NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | - NS_FRAME_HAS_DIRTY_CHILDREN); + RemoveStateBits(NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | + NS_FRAME_HAS_DIRTY_CHILDREN); nsRect overflow = nsRect(nsPoint(0,0), mRect.Size()); nsOverflowAreas overflowAreas(overflow, overflow); FinishAndStoreOverflow(overflowAreas, mRect.Size()); // XXX nsSVGContainerFrame::ReflowSVG only looks at its nsSVGDisplayableFrame // children, and calls ConsiderChildOverflow on them. Does it matter // that ConsiderChildOverflow won't be called on our children? @@ -4062,16 +4069,145 @@ SVGTextFrame::SelectSubString(nsIContent * Implements the SVG DOM GetSubStringLength method for the specified * text content element. */ nsresult SVGTextFrame::GetSubStringLength(nsIContent* aContent, uint32_t charnum, uint32_t nchars, float* aResult) { + // For some content we cannot (or currently cannot) compute the length + // without reflowing. In those cases we need to fall back to using + // GetSubStringLengthSlowFallback. + // + // We fall back for textPath since we need glyph positioning in order to + // tell if any characters should be ignored due to having fallen off the + // end of the textPath. + // + // We fall back for bidi because GetTrimmedOffsets does not produce the + // correct results for bidi continuations when passed aPostReflow = false. + // XXX It may be possible to determine which continuations to trim from (and + // which sides), but currently we don't do that. It would require us to + // identify the visual (rather than logical) start and end of the line, to + // avoid trimming at line-internal frame boundaries. Maybe nsBidiPresUtils + // methods like GetFrameToRightOf and GetFrameToLeftOf would help? + // + TextFrameIterator frameIter(this); + for (nsTextFrame* frame = frameIter.Current(); frame; frame = frameIter.Next()) { + if (frameIter.TextPathFrame() || + frame->GetNextContinuation()) { + return GetSubStringLengthSlowFallback(aContent, charnum, nchars, aResult); + } + } + + // We only need our text correspondence to be up to date (no need to call + // UpdateGlyphPositioning). + TextNodeCorrespondenceRecorder::RecordCorrespondence(this); + + // Convert charnum/nchars from addressable characters relative to + // aContent to global character indices. + CharIterator chit(this, CharIterator::eAddressable, aContent, + /* aPostReflow */ false); + if (!chit.AdvanceToSubtree() || + !chit.Next(charnum) || + chit.IsAfterSubtree()) { + return NS_ERROR_DOM_INDEX_SIZE_ERR; + } + + // We do this after the NS_ERROR_DOM_INDEX_SIZE_ERR return so JS calls + // correctly throw when necessary. + if (nchars == 0) { + *aResult = 0.0f; + return NS_OK; + } + + charnum = chit.TextElementCharIndex(); + chit.NextWithinSubtree(nchars); + nchars = chit.TextElementCharIndex() - charnum; + + // Sum of the substring advances. + nscoord textLength = 0; + + TextFrameIterator frit(this); // aSubtree = nullptr + + // Index of the first non-skipped char in the frame, and of a subsequent char + // that we're interested in. Both are relative to the index of the first + // non-skipped char in the ancestor <text> element. + uint32_t frameStartTextElementCharIndex = 0; + uint32_t textElementCharIndex; + + for (nsTextFrame* frame = frit.Current(); frame; frame = frit.Next()) { + frameStartTextElementCharIndex += frit.UndisplayedCharacters(); + textElementCharIndex = frameStartTextElementCharIndex; + + // Offset into frame's nsTextNode: + const uint32_t untrimmedOffset = frame->GetContentOffset(); + const uint32_t untrimmedLength = frame->GetContentEnd() - untrimmedOffset; + + // Trim the offset/length to remove any leading/trailing white space. + uint32_t trimmedOffset = untrimmedOffset; + uint32_t trimmedLength = untrimmedLength; + nsTextFrame::TrimmedOffsets trimmedOffsets = + frame->GetTrimmedOffsets(frame->GetContent()->GetText(), + /* aTrimAfter */ true, + /* aPostReflow */ false); + TrimOffsets(trimmedOffset, trimmedLength, trimmedOffsets); + + textElementCharIndex += trimmedOffset - untrimmedOffset; + + if (textElementCharIndex >= charnum + nchars) { + break; // we're past the end of the substring + } + + uint32_t offset = textElementCharIndex; + + // Intersect the substring we are interested in with the range covered by + // the nsTextFrame. + IntersectInterval(offset, trimmedLength, charnum, nchars); + + if (trimmedLength != 0) { + // Convert offset into an index into the frame. + offset += trimmedOffset - textElementCharIndex; + + gfxSkipCharsIterator skipCharsIter = + frame->EnsureTextRun(nsTextFrame::eInflated); + gfxTextRun* textRun = frame->GetTextRun(nsTextFrame::eInflated); + Range range = + ConvertOriginalToSkipped(skipCharsIter, offset, trimmedLength); + + // Accumulate the advance. + textLength += textRun->GetAdvanceWidth(range, nullptr); + } + + // Advance, ready for next call: + frameStartTextElementCharIndex += untrimmedLength; + } + + nsPresContext* presContext = PresContext(); + float cssPxPerDevPx = presContext-> + AppUnitsToFloatCSSPixels(presContext->AppUnitsPerDevPixel()); + + *aResult = presContext->AppUnitsToGfxUnits(textLength) * + cssPxPerDevPx / mFontSizeScaleFactor; + return NS_OK; +} + +nsresult +SVGTextFrame::GetSubStringLengthSlowFallback(nsIContent* aContent, + uint32_t charnum, uint32_t nchars, + float* aResult) +{ + // We need to make sure that we've been reflowed before updating the glyph + // positioning. + // XXX perf: It may be possible to limit reflow to just calling ReflowSVG, + // but we would still need to resort to full reflow for percentage + // positioning attributes. For now we just do a full reflow regardless since + // the cases that would cause us to be called are relatively uncommon. + PresContext()->PresShell()->FlushPendingNotifications(FlushType::Layout); + UpdateGlyphPositioning(); // Convert charnum/nchars from addressable characters relative to // aContent to global character indices. CharIterator chit(this, CharIterator::eAddressable, aContent); if (!chit.AdvanceToSubtree() || !chit.Next(charnum) || chit.IsAfterSubtree()) { @@ -4804,17 +4940,17 @@ SVGTextFrame::AdjustPositionsForClusters it.Next(); } } SVGPathElement* SVGTextFrame::GetTextPathPathElement(nsIFrame* aTextPathFrame) { nsSVGTextPathProperty *property = - aTextPathFrame->GetProperty(nsSVGEffects::HrefAsTextPathProperty()); + aTextPathFrame->GetProperty(SVGObserverUtils::HrefAsTextPathProperty()); if (!property) { nsIContent* content = aTextPathFrame->GetContent(); dom::SVGTextPathElement* tp = static_cast<dom::SVGTextPathElement*>(content); nsAutoString href; if (tp->mStringAttributes[dom::SVGTextPathElement::HREF].IsExplicitlySet()) { tp->mStringAttributes[dom::SVGTextPathElement::HREF] .GetAnimValue(href, tp); @@ -4827,20 +4963,20 @@ SVGTextFrame::GetTextPathPathElement(nsI return nullptr; // no URL } nsCOMPtr<nsIURI> targetURI; nsCOMPtr<nsIURI> base = content->GetBaseURI(); nsContentUtils::NewURIWithDocumentCharset(getter_AddRefs(targetURI), href, content->GetUncomposedDoc(), base); - property = nsSVGEffects::GetTextPathProperty( + property = SVGObserverUtils::GetTextPathProperty( targetURI, aTextPathFrame, - nsSVGEffects::HrefAsTextPathProperty()); + SVGObserverUtils::HrefAsTextPathProperty()); if (!property) return nullptr; } Element* element = property->GetReferencedElement(); return (element && element->IsSVGElement(nsGkAtoms::path)) ? static_cast<SVGPathElement*>(element) : nullptr; } @@ -5031,16 +5167,20 @@ SVGTextFrame::DoGlyphPositioning() RemoveStateBits(NS_STATE_SVG_POSITIONING_DIRTY); nsIFrame* kid = PrincipalChildList().FirstChild(); if (kid && NS_SUBTREE_DIRTY(kid)) { MOZ_ASSERT(false, "should have already reflowed the kid"); return; } + // Since we can be called directly via GetBBoxContribution, our correspondence + // may not be up to date. + TextNodeCorrespondenceRecorder::RecordCorrespondence(this); + // Determine the positions of each character in app units. nsTArray<nsPoint> charPositions; DetermineCharPositions(charPositions); if (charPositions.IsEmpty()) { // No characters, so nothing to do. return; } @@ -5217,17 +5357,21 @@ SVGTextFrame::ScheduleReflowSVG() } else { nsSVGUtils::ScheduleReflowSVG(this); } } void SVGTextFrame::NotifyGlyphMetricsChange() { - AddStateBits(NS_STATE_SVG_POSITIONING_DIRTY); + // TODO: perf - adding NS_STATE_SVG_TEXT_CORRESPONDENCE_DIRTY is overly + // aggressive here. Ideally we would only set that bit when our descendant + // frame tree changes (i.e. after frame construction). + AddStateBits(NS_STATE_SVG_TEXT_CORRESPONDENCE_DIRTY | + NS_STATE_SVG_POSITIONING_DIRTY); nsLayoutUtils::PostRestyleEvent( mContent->AsElement(), nsRestyleHint(0), nsChangeHint_InvalidateRenderingObservers); ScheduleReflowSVG(); } void SVGTextFrame::UpdateGlyphPositioning() @@ -5269,58 +5413,66 @@ SVGTextFrame::MaybeReflowAnonymousBlockC if (NS_SUBTREE_DIRTY(this)) { if (mState & NS_FRAME_IS_DIRTY) { // If we require a full reflow, ensure our kid is marked fully dirty. // (Note that our anonymous nsBlockFrame is not an nsSVGDisplayableFrame, so // even when we are called via our ReflowSVG this will not be done for us // by nsSVGDisplayContainerFrame::ReflowSVG.) kid->AddStateBits(NS_FRAME_IS_DIRTY); } + + TextNodeCorrespondenceRecorder::RecordCorrespondence(this); + MOZ_ASSERT(nsSVGUtils::AnyOuterSVGIsCallingReflowSVG(this), "should be under ReflowSVG"); nsPresContext::InterruptPreventer noInterrupts(PresContext()); DoReflow(); } } void SVGTextFrame::DoReflow() { // Since we are going to reflow the anonymous block frame, we will // need to update mPositions. - AddStateBits(NS_STATE_SVG_POSITIONING_DIRTY); + // We also mark our text correspondence as dirty since we can end up needing + // reflow in ways that do not set NS_STATE_SVG_TEXT_CORRESPONDENCE_DIRTY. + // (We'd then fail the "expected a TextNodeCorrespondenceProperty" assertion + // when UpdateGlyphPositioning() is called after we return.) + AddStateBits(NS_STATE_SVG_TEXT_CORRESPONDENCE_DIRTY | + NS_STATE_SVG_POSITIONING_DIRTY); if (mState & NS_FRAME_IS_NONDISPLAY) { // Normally, these dirty flags would be cleared in ReflowSVG(), but that // doesn't get called for non-display frames. We don't want to reflow our // descendants every time SVGTextFrame::PaintSVG makes sure that we have // valid positions by calling UpdateGlyphPositioning(), so we need to clear // these dirty bits. Note that this also breaks an invalidation loop where // our descendants invalidate as they reflow, which invalidates rendering // observers, which reschedules the frame that is currently painting by // referencing us to paint again. See bug 839958 comment 7. Hopefully we // will break that loop more convincingly at some point. - mState &= ~(NS_FRAME_IS_DIRTY | NS_FRAME_HAS_DIRTY_CHILDREN); + RemoveStateBits(NS_FRAME_IS_DIRTY | NS_FRAME_HAS_DIRTY_CHILDREN); } nsPresContext *presContext = PresContext(); nsIFrame* kid = PrincipalChildList().FirstChild(); if (!kid) return; RefPtr<gfxContext> renderingContext = presContext->PresShell()->CreateReferenceRenderingContext(); if (UpdateFontSizeScaleFactor()) { // If the font size scale factor changed, we need the block to report // an updated preferred width. kid->MarkIntrinsicISizesDirty(); } - mState |= NS_STATE_SVG_TEXT_IN_REFLOW; + AddStateBits(NS_STATE_SVG_TEXT_IN_REFLOW); nscoord inlineSize = kid->GetPrefISize(renderingContext); WritingMode wm = kid->GetWritingMode(); ReflowInput reflowInput(presContext, kid, renderingContext, LogicalSize(wm, inlineSize, NS_UNCONSTRAINEDSIZE)); ReflowOutput desiredSize(reflowInput); @@ -5330,19 +5482,17 @@ SVGTextFrame::DoReflow() reflowInput.ComputedPhysicalMargin() == nsMargin(0, 0, 0, 0), "style system should ensure that :-moz-svg-text " "does not get styled"); kid->Reflow(presContext, desiredSize, reflowInput, status); kid->DidReflow(presContext, &reflowInput, nsDidReflowStatus::FINISHED); kid->SetSize(wm, desiredSize.Size(wm)); - mState &= ~NS_STATE_SVG_TEXT_IN_REFLOW; - - TextNodeCorrespondenceRecorder::RecordCorrespondence(this); + RemoveStateBits(NS_STATE_SVG_TEXT_IN_REFLOW); } // Usable font size range in devpixels / user-units #define CLAMP_MIN_SIZE 8.0 #define CLAMP_MAX_SIZE 200.0 #define PRECISE_SIZE 200.0 bool
--- a/layout/svg/SVGTextFrame.h +++ b/layout/svg/SVGTextFrame.h @@ -198,17 +198,18 @@ class SVGTextFrame final : public nsSVGD protected: explicit SVGTextFrame(nsStyleContext* aContext) : nsSVGDisplayContainerFrame(aContext, kClassID) , mTrailingUndisplayedCharacters(0) , mFontSizeScaleFactor(1.0f) , mLastContextScale(1.0f) , mLengthAdjustScaleFactor(1.0f) { - AddStateBits(NS_STATE_SVG_POSITIONING_DIRTY); + AddStateBits(NS_STATE_SVG_TEXT_CORRESPONDENCE_DIRTY | + NS_STATE_SVG_POSITIONING_DIRTY); } ~SVGTextFrame() {} public: NS_DECL_QUERYFRAME NS_DECL_FRAMEARENA_HELPERS(SVGTextFrame) @@ -413,16 +414,28 @@ private: /** * Populates mPositions with positioning information for each character * within the <text>. */ void DoGlyphPositioning(); /** + * This fallback version of GetSubStringLength that flushes layout and takes + * into account glyph positioning. As per the SVG 2 spec, typically glyph + * positioning does not affect the results of getSubStringLength, but one + * exception is text in a textPath where we need to ignore characters that + * fall off the end of the textPath path. + */ + nsresult GetSubStringLengthSlowFallback(nsIContent* aContent, + uint32_t charnum, + uint32_t nchars, + float* aResult); + + /** * Converts the specified index into mPositions to an addressable * character index (as can be used with the SVG DOM text methods) * relative to the specified text child content element. * * @param aIndex The global character index. * @param aContent The descendant text child content element that * the returned addressable index will be relative to; null * means the same as the <text> element.
--- a/layout/svg/moz.build +++ b/layout/svg/moz.build @@ -12,38 +12,37 @@ if CONFIG['ENABLE_TESTS']: 'tests/mochitest.ini', ] MOCHITEST_CHROME_MANIFESTS += [ 'tests/chrome.ini', ] EXPORTS += [ 'nsFilterInstance.h', - 'nsSVGEffects.h', 'nsSVGFilterInstance.h', 'nsSVGForeignObjectFrame.h', 'nsSVGImageFrame.h', 'nsSVGIntegrationUtils.h', 'nsSVGUseFrame.h', 'nsSVGUtils.h', 'SVGImageContext.h', + 'SVGObserverUtils.h', ] EXPORTS.mozilla += [ 'SVGContextPaint.h', ] UNIFIED_SOURCES += [ 'nsCSSClipPathInstance.cpp', 'nsCSSFilterInstance.cpp', 'nsFilterInstance.cpp', 'nsSVGAFrame.cpp', 'nsSVGClipPathFrame.cpp', 'nsSVGContainerFrame.cpp', - 'nsSVGEffects.cpp', 'nsSVGFilterFrame.cpp', 'nsSVGFilterInstance.cpp', 'nsSVGForeignObjectFrame.cpp', 'nsSVGGenericContainerFrame.cpp', 'nsSVGGFrame.cpp', 'nsSVGGradientFrame.cpp', 'nsSVGImageFrame.cpp', 'nsSVGInnerSVGFrame.cpp', @@ -60,16 +59,17 @@ UNIFIED_SOURCES += [ 'nsSVGViewportFrame.cpp', 'SVGContextPaint.cpp', 'SVGFEContainerFrame.cpp', 'SVGFEImageFrame.cpp', 'SVGFELeafFrame.cpp', 'SVGFEUnstyledLeafFrame.cpp', 'SVGGeometryFrame.cpp', 'SVGImageContext.cpp', + 'SVGObserverUtils.cpp', 'SVGTextFrame.cpp', 'SVGViewFrame.cpp', ] FINAL_LIBRARY = 'xul' LOCAL_INCLUDES += [ '../../widget', '../base',
--- a/layout/svg/nsSVGClipPathFrame.cpp +++ b/layout/svg/nsSVGClipPathFrame.cpp @@ -7,17 +7,17 @@ #include "nsSVGClipPathFrame.h" // Keep others in (case-insensitive) order: #include "AutoReferenceChainGuard.h" #include "DrawResult.h" #include "gfxContext.h" #include "mozilla/dom/SVGClipPathElement.h" #include "nsGkAtoms.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "SVGGeometryElement.h" #include "SVGGeometryFrame.h" #include "nsSVGUtils.h" using namespace mozilla; using namespace mozilla::dom; using namespace mozilla::gfx; using namespace mozilla::image; @@ -141,17 +141,17 @@ nsSVGClipPathFrame::PaintClipMask(gfxCon // Paint this clipPath's contents into aMaskDT: // We need to set mMatrixForChildren here so that under the PaintSVG calls // on our children (below) our GetCanvasTM() method will return the correct // transform. mMatrixForChildren = GetClipPathTransform(aClippedFrame) * aMatrix; // Check if this clipPath is itself clipped by another clipPath: nsSVGClipPathFrame* clipPathThatClipsClipPath = - nsSVGEffects::GetEffectProperties(this).GetClipPathFrame(); + SVGObserverUtils::GetEffectProperties(this).GetClipPathFrame(); nsSVGUtils::MaskUsage maskUsage; nsSVGUtils::DetermineMaskUsage(this, true, maskUsage); if (maskUsage.shouldApplyClipPath) { clipPathThatClipsClipPath->ApplyClipPath(aMaskContext, aClippedFrame, aMatrix); } else if (maskUsage.shouldGenerateClipMaskLayer) { Matrix maskTransform; @@ -197,18 +197,18 @@ nsSVGClipPathFrame::PaintFrameIntoMask(n if (!frame) { return; } // The CTM of each frame referencing us can be different. frame->NotifySVGChanged(nsSVGDisplayableFrame::TRANSFORM_CHANGED); // Children of this clipPath may themselves be clipped. - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(aFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(aFrame); if (effectProperties.HasInvalidClipPath()) { return; } nsSVGClipPathFrame *clipPathThatClipsChild = effectProperties.GetClipPathFrame(); nsSVGUtils::MaskUsage maskUsage; nsSVGUtils::DetermineMaskUsage(aFrame, true, maskUsage); @@ -301,17 +301,17 @@ nsSVGClipPathFrame::PointIsInsideClipPat gfxPoint point = matrix.TransformPoint(aPoint); // clipPath elements can themselves be clipped by a different clip path. In // that case the other clip path further clips away the element that is being // clipped by the original clipPath. If this clipPath is being clipped by a // different clip path we need to check if it prevents the original element // from recieving events at aPoint: nsSVGClipPathFrame *clipPathFrame = - nsSVGEffects::GetEffectProperties(this).GetClipPathFrame(); + SVGObserverUtils::GetEffectProperties(this).GetClipPathFrame(); if (clipPathFrame && !clipPathFrame->PointIsInsideClipPath(aClippedFrame, aPoint)) { return false; } for (nsIFrame* kid = mFrames.FirstChild(); kid; kid = kid->GetNextSibling()) { nsSVGDisplayableFrame* SVGFrame = do_QueryFrame(kid); @@ -333,17 +333,17 @@ nsSVGClipPathFrame::PointIsInsideClipPat return false; } bool nsSVGClipPathFrame::IsTrivial(nsSVGDisplayableFrame **aSingleChild) { // If the clip path is clipped then it's non-trivial - if (nsSVGEffects::GetEffectProperties(this).GetClipPathFrame()) + if (SVGObserverUtils::GetEffectProperties(this).GetClipPathFrame()) return false; if (aSingleChild) { *aSingleChild = nullptr; } nsSVGDisplayableFrame* foundChild = nullptr; @@ -352,17 +352,17 @@ nsSVGClipPathFrame::IsTrivial(nsSVGDispl nsSVGDisplayableFrame* svgChild = do_QueryFrame(kid); if (svgChild) { // We consider a non-trivial clipPath to be one containing // either more than one svg child and/or a svg container if (foundChild || svgChild->IsDisplayContainer()) return false; // or where the child is itself clipped - if (nsSVGEffects::GetEffectProperties(kid).GetClipPathFrame()) + if (SVGObserverUtils::GetEffectProperties(kid).GetClipPathFrame()) return false; foundChild = svgChild; } } if (aSingleChild) { *aSingleChild = foundChild; } @@ -378,17 +378,17 @@ nsSVGClipPathFrame::IsValid() // that must all be applied. We re-enter this method for each clipPath in a // chain, so we need to protect against reference chain related crashes etc.: AutoReferenceChainGuard refChainGuard(this, &mIsBeingProcessed, &sRefChainLengthCounter); if (MOZ_UNLIKELY(!refChainGuard.Reference())) { return false; // Break reference chain } - if (nsSVGEffects::GetEffectProperties(this).HasInvalidClipPath()) { + if (SVGObserverUtils::GetEffectProperties(this).HasInvalidClipPath()) { return false; } for (nsIFrame* kid = mFrames.FirstChild(); kid; kid = kid->GetNextSibling()) { LayoutFrameType kidType = kid->Type(); @@ -416,22 +416,22 @@ nsSVGClipPathFrame::IsValid() nsresult nsSVGClipPathFrame::AttributeChanged(int32_t aNameSpaceID, nsIAtom* aAttribute, int32_t aModType) { if (aNameSpaceID == kNameSpaceID_None) { if (aAttribute == nsGkAtoms::transform) { - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); nsSVGUtils::NotifyChildrenOfSVGChange(this, nsSVGDisplayableFrame::TRANSFORM_CHANGED); } if (aAttribute == nsGkAtoms::clipPathUnits) { - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); } } return nsSVGContainerFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType); } void @@ -481,33 +481,33 @@ nsSVGClipPathFrame::GetBBoxForClipPathFr for (; node; node = node->GetNextSibling()) { nsIFrame *frame = static_cast<nsSVGElement*>(node)->GetPrimaryFrame(); if (frame) { nsSVGDisplayableFrame* svg = do_QueryFrame(frame); if (svg) { tmpBBox = svg->GetBBoxContribution(mozilla::gfx::ToMatrix(aMatrix), nsSVGUtils::eBBoxIncludeFill); - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(frame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(frame); if (effectProperties.HasNoOrValidClipPath()) { nsSVGClipPathFrame *clipPathFrame = effectProperties.GetClipPathFrame(); if (clipPathFrame) { tmpBBox = clipPathFrame->GetBBoxForClipPathFrame(tmpBBox, aMatrix); } } tmpBBox.Intersect(aBBox); unionBBox.UnionEdges(tmpBBox); } } } - nsSVGEffects::EffectProperties props = - nsSVGEffects::GetEffectProperties(this); + SVGObserverUtils::EffectProperties props = + SVGObserverUtils::GetEffectProperties(this); if (props.mClipPath) { if (props.HasInvalidClipPath()) { unionBBox = SVGBBox(); } else { nsSVGClipPathFrame *clipPathFrame = props.GetClipPathFrame(); if (clipPathFrame) { tmpBBox = clipPathFrame->GetBBoxForClipPathFrame(aBBox, aMatrix); unionBBox.Intersect(tmpBBox);
--- a/layout/svg/nsSVGContainerFrame.cpp +++ b/layout/svg/nsSVGContainerFrame.cpp @@ -6,17 +6,17 @@ // Main header first: #include "nsSVGContainerFrame.h" // Keep others in (case-insensitive) order: #include "DrawResult.h" #include "mozilla/RestyleManager.h" #include "mozilla/RestyleManagerInlines.h" #include "nsCSSFrameConstructor.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGElement.h" #include "nsSVGUtils.h" #include "nsSVGAnimatedTransformList.h" #include "SVGTextFrame.h" using namespace mozilla; using namespace mozilla::image; @@ -195,17 +195,17 @@ nsSVGDisplayContainerFrame::InsertFrames } } } void nsSVGDisplayContainerFrame::RemoveFrame(ChildListID aListID, nsIFrame* aOldFrame) { - nsSVGEffects::InvalidateRenderingObservers(aOldFrame); + SVGObserverUtils::InvalidateRenderingObservers(aOldFrame); // nsSVGContainerFrame::RemoveFrame doesn't call down into // nsContainerFrame::RemoveFrame, so it doesn't call FrameNeedsReflow. We // need to schedule a repaint and schedule an update to our overflow rects. SchedulePaint(); PresContext()->RestyleManager()->PostRestyleEvent( mContent->AsElement(), nsRestyleHint(0), nsChangeHint_UpdateOverflow); @@ -329,17 +329,17 @@ nsSVGDisplayContainerFrame::ReflowSVG() // the initial reflow is currently underway. bool isFirstReflow = (mState & NS_FRAME_FIRST_REFLOW); bool outerSVGHasHadFirstReflow = (GetParent()->GetStateBits() & NS_FRAME_FIRST_REFLOW) == 0; if (outerSVGHasHadFirstReflow) { - mState &= ~NS_FRAME_FIRST_REFLOW; // tell our children + RemoveStateBits(NS_FRAME_FIRST_REFLOW); // tell our children } nsOverflowAreas overflowRects; for (nsIFrame* kid = mFrames.FirstChild(); kid; kid = kid->GetNextSibling()) { nsSVGDisplayableFrame* SVGFrame = do_QueryFrame(kid); if (SVGFrame) { @@ -379,25 +379,25 @@ nsSVGDisplayContainerFrame::ReflowSVG() mRect.Size() == nsSize(0,0)) || mRect.IsEqualEdges(nsRect()), "Only inner-<svg>/<use> is expected to have mRect set"); if (isFirstReflow) { // Make sure we have our filter property (if any) before calling // FinishAndStoreOverflow (subsequent filter changes are handled off // nsChangeHint_UpdateEffects): - nsSVGEffects::UpdateEffects(this); + SVGObserverUtils::UpdateEffects(this); } FinishAndStoreOverflow(overflowRects, mRect.Size()); // Remove state bits after FinishAndStoreOverflow so that it doesn't // invalidate on first reflow: - mState &= ~(NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | - NS_FRAME_HAS_DIRTY_CHILDREN); + RemoveStateBits(NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | + NS_FRAME_HAS_DIRTY_CHILDREN); } void nsSVGDisplayContainerFrame::NotifySVGChanged(uint32_t aFlags) { MOZ_ASSERT(aFlags & (TRANSFORM_CHANGED | COORD_CONTEXT_CHANGED), "Invalidation logic may need adjusting");
--- a/layout/svg/nsSVGFilterFrame.cpp +++ b/layout/svg/nsSVGFilterFrame.cpp @@ -5,17 +5,17 @@ // Main header first: #include "nsSVGFilterFrame.h" // Keep others in (case-insensitive) order: #include "AutoReferenceChainGuard.h" #include "gfxUtils.h" #include "nsGkAtoms.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGElement.h" #include "mozilla/dom/SVGFilterElement.h" #include "nsSVGFilterInstance.h" #include "nsSVGIntegrationUtils.h" #include "nsSVGUtils.h" #include "nsContentUtils.h" using namespace mozilla; @@ -112,17 +112,17 @@ nsSVGFilterFrame::GetFilterContent(nsICo nsSVGFilterFrame * nsSVGFilterFrame::GetReferencedFilter() { if (mNoHRefURI) return nullptr; nsSVGPaintingProperty *property = - GetProperty(nsSVGEffects::HrefAsPaintingProperty()); + GetProperty(SVGObserverUtils::HrefAsPaintingProperty()); if (!property) { // Fetch our Filter element's href or xlink:href attribute SVGFilterElement *filter = static_cast<SVGFilterElement *>(GetContent()); nsAutoString href; if (filter->mStringAttributes[SVGFilterElement::HREF].IsExplicitlySet()) { filter->mStringAttributes[SVGFilterElement::HREF] .GetAnimValue(href, filter); @@ -138,18 +138,18 @@ nsSVGFilterFrame::GetReferencedFilter() // Convert href to an nsIURI nsCOMPtr<nsIURI> targetURI; nsCOMPtr<nsIURI> base = mContent->GetBaseURI(); nsContentUtils::NewURIWithDocumentCharset(getter_AddRefs(targetURI), href, mContent->GetUncomposedDoc(), base); property = - nsSVGEffects::GetPaintingProperty(targetURI, this, - nsSVGEffects::HrefAsPaintingProperty()); + SVGObserverUtils::GetPaintingProperty(targetURI, this, + SVGObserverUtils::HrefAsPaintingProperty()); if (!property) return nullptr; } nsIFrame *result = property->GetReferencedFrame(); if (!result) return nullptr; @@ -167,25 +167,25 @@ nsSVGFilterFrame::AttributeChanged(int32 { if (aNameSpaceID == kNameSpaceID_None && (aAttribute == nsGkAtoms::x || aAttribute == nsGkAtoms::y || aAttribute == nsGkAtoms::width || aAttribute == nsGkAtoms::height || aAttribute == nsGkAtoms::filterUnits || aAttribute == nsGkAtoms::primitiveUnits)) { - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); } else if ((aNameSpaceID == kNameSpaceID_XLink || aNameSpaceID == kNameSpaceID_None) && aAttribute == nsGkAtoms::href) { // Blow away our reference, if any - DeleteProperty(nsSVGEffects::HrefAsPaintingProperty()); + DeleteProperty(SVGObserverUtils::HrefAsPaintingProperty()); mNoHRefURI = false; // And update whoever references us - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); } return nsSVGContainerFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType); } #ifdef DEBUG void nsSVGFilterFrame::Init(nsIContent* aContent,
--- a/layout/svg/nsSVGFilterInstance.cpp +++ b/layout/svg/nsSVGFilterInstance.cpp @@ -8,17 +8,17 @@ // Keep others in (case-insensitive) order: #include "gfxPlatform.h" #include "gfxUtils.h" #include "nsSVGDisplayableFrame.h" #include "mozilla/dom/HTMLCanvasElement.h" #include "mozilla/dom/SVGFilterElement.h" #include "nsReferencedElement.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGFilterFrame.h" #include "nsSVGUtils.h" #include "SVGContentUtils.h" #include "FilterSupport.h" #include "gfx2DGlue.h" using namespace mozilla; using namespace mozilla::dom; @@ -121,17 +121,17 @@ nsSVGFilterInstance::GetFilterFrame(nsIF // filter element. if (!mTargetContent) { return nullptr; } // aTargetFrame can be null if this filter belongs to a // CanvasRenderingContext2D. nsCOMPtr<nsIURI> url = aTargetFrame - ? nsSVGEffects::GetFilterURI(aTargetFrame, mFilter) + ? SVGObserverUtils::GetFilterURI(aTargetFrame, mFilter) : mFilter.GetURL()->ResolveLocalRef(mTargetContent); if (!url) { NS_NOTREACHED("an nsStyleFilter of type URL should have a non-null URL"); return nullptr; } // Look up the filter element by URL.
--- a/layout/svg/nsSVGForeignObjectFrame.cpp +++ b/layout/svg/nsSVGForeignObjectFrame.cpp @@ -10,17 +10,17 @@ #include "DrawResult.h" #include "gfxContext.h" #include "nsDisplayList.h" #include "nsGkAtoms.h" #include "nsNameSpaceManager.h" #include "nsLayoutUtils.h" #include "nsRegion.h" #include "nsSVGContainerFrame.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "mozilla/dom/SVGForeignObjectElement.h" #include "nsSVGIntegrationUtils.h" #include "nsSVGOuterSVGFrame.h" #include "nsSVGUtils.h" #include "mozilla/AutoRestore.h" using namespace mozilla; using namespace mozilla::dom; @@ -355,34 +355,34 @@ nsSVGForeignObjectFrame::ReflowSVG() nsPresContext::InterruptPreventer noInterrupts(PresContext()); DoReflow(); if (mState & NS_FRAME_FIRST_REFLOW) { // Make sure we have our filter property (if any) before calling // FinishAndStoreOverflow (subsequent filter changes are handled off // nsChangeHint_UpdateEffects): - nsSVGEffects::UpdateEffects(this); + SVGObserverUtils::UpdateEffects(this); } // If we have a filter, we need to invalidate ourselves because filter // output can change even if none of our descendants need repainting. if (StyleEffects()->HasFilters()) { InvalidateFrame(); } // TODO: once we support |overflow:visible| on foreignObject, then we will // need to take account of our descendants here. nsRect overflow = nsRect(nsPoint(0,0), mRect.Size()); nsOverflowAreas overflowAreas(overflow, overflow); FinishAndStoreOverflow(overflowAreas, mRect.Size()); // Now unset the various reflow bits: - mState &= ~(NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | - NS_FRAME_HAS_DIRTY_CHILDREN); + RemoveStateBits(NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | + NS_FRAME_HAS_DIRTY_CHILDREN); } void nsSVGForeignObjectFrame::NotifySVGChanged(uint32_t aFlags) { MOZ_ASSERT(aFlags & (TRANSFORM_CHANGED | COORD_CONTEXT_CHANGED), "Invalidation logic may need adjusting");
--- a/layout/svg/nsSVGGradientFrame.cpp +++ b/layout/svg/nsSVGGradientFrame.cpp @@ -8,17 +8,17 @@ #include <algorithm> // Keep others in (case-insensitive) order: #include "AutoReferenceChainGuard.h" #include "gfxPattern.h" #include "mozilla/dom/SVGGradientElement.h" #include "mozilla/dom/SVGStopElement.h" #include "nsContentUtils.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGAnimatedTransformList.h" // XXX Tight coupling with content classes ahead! using namespace mozilla; using namespace mozilla::dom; using namespace mozilla::gfx; @@ -41,25 +41,25 @@ nsresult nsSVGGradientFrame::AttributeChanged(int32_t aNameSpaceID, nsIAtom* aAttribute, int32_t aModType) { if (aNameSpaceID == kNameSpaceID_None && (aAttribute == nsGkAtoms::gradientUnits || aAttribute == nsGkAtoms::gradientTransform || aAttribute == nsGkAtoms::spreadMethod)) { - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); } else if ((aNameSpaceID == kNameSpaceID_XLink || aNameSpaceID == kNameSpaceID_None) && aAttribute == nsGkAtoms::href) { // Blow away our reference, if any - DeleteProperty(nsSVGEffects::HrefAsPaintingProperty()); + DeleteProperty(SVGObserverUtils::HrefAsPaintingProperty()); mNoHRefURI = false; // And update whoever references us - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); } return nsSVGPaintServerFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType); } //---------------------------------------------------------------------- @@ -330,17 +330,17 @@ nsSVGGradientFrame::GetPaintServerPatter nsSVGGradientFrame * nsSVGGradientFrame::GetReferencedGradient() { if (mNoHRefURI) return nullptr; nsSVGPaintingProperty *property = - GetProperty(nsSVGEffects::HrefAsPaintingProperty()); + GetProperty(SVGObserverUtils::HrefAsPaintingProperty()); if (!property) { // Fetch our gradient element's href or xlink:href attribute dom::SVGGradientElement* grad = static_cast<dom::SVGGradientElement*>(GetContent()); nsAutoString href; if (grad->mStringAttributes[dom::SVGGradientElement::HREF] .IsExplicitlySet()) { @@ -358,18 +358,18 @@ nsSVGGradientFrame::GetReferencedGradien // Convert href to an nsIURI nsCOMPtr<nsIURI> targetURI; nsCOMPtr<nsIURI> base = mContent->GetBaseURI(); nsContentUtils::NewURIWithDocumentCharset(getter_AddRefs(targetURI), href, mContent->GetUncomposedDoc(), base); property = - nsSVGEffects::GetPaintingProperty(targetURI, this, - nsSVGEffects::HrefAsPaintingProperty()); + SVGObserverUtils::GetPaintingProperty(targetURI, this, + SVGObserverUtils::HrefAsPaintingProperty()); if (!property) return nullptr; } nsIFrame *result = property->GetReferencedFrame(); if (!result) return nullptr; @@ -435,17 +435,17 @@ nsSVGLinearGradientFrame::AttributeChang nsIAtom* aAttribute, int32_t aModType) { if (aNameSpaceID == kNameSpaceID_None && (aAttribute == nsGkAtoms::x1 || aAttribute == nsGkAtoms::y1 || aAttribute == nsGkAtoms::x2 || aAttribute == nsGkAtoms::y2)) { - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); } return nsSVGGradientFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType); } //---------------------------------------------------------------------- @@ -538,17 +538,17 @@ nsSVGRadialGradientFrame::AttributeChang int32_t aModType) { if (aNameSpaceID == kNameSpaceID_None && (aAttribute == nsGkAtoms::r || aAttribute == nsGkAtoms::cx || aAttribute == nsGkAtoms::cy || aAttribute == nsGkAtoms::fx || aAttribute == nsGkAtoms::fy)) { - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); } return nsSVGGradientFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType); } //----------------------------------------------------------------------
--- a/layout/svg/nsSVGImageFrame.cpp +++ b/layout/svg/nsSVGImageFrame.cpp @@ -10,17 +10,17 @@ #include "gfxPlatform.h" #include "mozilla/gfx/2D.h" #include "imgIContainer.h" #include "nsContainerFrame.h" #include "nsIDOMMutationEvent.h" #include "nsIImageLoadingContent.h" #include "nsLayoutUtils.h" #include "imgINotificationObserver.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "mozilla/dom/SVGSVGElement.h" #include "nsSVGUtils.h" #include "SVGContentUtils.h" #include "SVGGeometryFrame.h" #include "SVGImageContext.h" #include "mozilla/dom/SVGImageElement.h" #include "nsContentUtils.h" #include "nsIReflowCallback.h" @@ -443,31 +443,31 @@ nsSVGImageFrame::ReflowSVG() } else { mRect.SetEmpty(); } if (mState & NS_FRAME_FIRST_REFLOW) { // Make sure we have our filter property (if any) before calling // FinishAndStoreOverflow (subsequent filter changes are handled off // nsChangeHint_UpdateEffects): - nsSVGEffects::UpdateEffects(this); + SVGObserverUtils::UpdateEffects(this); if (!mReflowCallbackPosted) { nsIPresShell* shell = PresContext()->PresShell(); mReflowCallbackPosted = true; shell->PostReflowCallback(this); } } nsRect overflow = nsRect(nsPoint(0,0), mRect.Size()); nsOverflowAreas overflowAreas(overflow, overflow); FinishAndStoreOverflow(overflowAreas, mRect.Size()); - mState &= ~(NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | - NS_FRAME_HAS_DIRTY_CHILDREN); + RemoveStateBits(NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | + NS_FRAME_HAS_DIRTY_CHILDREN); // Invalidate, but only if this is not our first reflow (since if it is our // first reflow then we haven't had our first paint yet). if (!(GetParent()->GetStateBits() & NS_FRAME_FIRST_REFLOW)) { InvalidateFrame(); } }
--- a/layout/svg/nsSVGImageFrame.h +++ b/layout/svg/nsSVGImageFrame.h @@ -11,17 +11,17 @@ #include "gfxPlatform.h" #include "mozilla/gfx/2D.h" #include "imgIContainer.h" #include "nsContainerFrame.h" #include "nsIDOMMutationEvent.h" #include "nsIImageLoadingContent.h" #include "nsLayoutUtils.h" #include "imgINotificationObserver.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "mozilla/dom/SVGSVGElement.h" #include "nsSVGUtils.h" #include "SVGContentUtils.h" #include "SVGGeometryFrame.h" #include "SVGImageContext.h" #include "mozilla/dom/SVGImageElement.h" #include "nsContentUtils.h" #include "nsIReflowCallback.h"
--- a/layout/svg/nsSVGIntegrationUtils.cpp +++ b/layout/svg/nsSVGIntegrationUtils.cpp @@ -11,17 +11,17 @@ #include "gfxPrefs.h" #include "nsCSSAnonBoxes.h" #include "nsCSSClipPathInstance.h" #include "nsDisplayList.h" #include "nsFilterInstance.h" #include "nsLayoutUtils.h" #include "gfxContext.h" #include "nsSVGClipPathFrame.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGElement.h" #include "nsSVGFilterPaintCallback.h" #include "nsSVGMaskFrame.h" #include "nsSVGPaintServerFrame.h" #include "nsSVGUtils.h" #include "FrameLayerBuilder.h" #include "BasicLayers.h" #include "mozilla/gfx/Point.h" @@ -279,18 +279,18 @@ nsRect ComputePostEffectsVisualOverflowRect(nsIFrame* aFrame, const nsRect& aPreEffectsOverflowRect) { NS_ASSERTION(!(aFrame->GetStateBits() & NS_FRAME_SVG_LAYOUT), "Don't call this on SVG child frames"); nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(aFrame); - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(firstFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(firstFrame); if (!effectProperties.HasValidFilter()) { return aPreEffectsOverflowRect; } // Create an override bbox - see comment above: nsPoint firstFrameToBoundingBox = GetOffsetToBoundingBox(firstFrame); // overrideBBox is in "user space", in _CSS_ pixels: // XXX Why are we rounding out to pixel boundaries? We don't do that in @@ -319,17 +319,17 @@ nsSVGIntegrationUtils::AdjustInvalidArea if (aInvalidRegion.IsEmpty()) { return nsIntRect(); } // Don't bother calling GetEffectProperties; the filter property should // already have been set up during reflow/ComputeFrameEffectsRect nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(aFrame); - nsSVGFilterProperty *prop = nsSVGEffects::GetFilterProperty(firstFrame); + nsSVGFilterProperty *prop = SVGObserverUtils::GetFilterProperty(firstFrame); if (!prop || !prop->IsInObserverLists()) { return aInvalidRegion; } int32_t appUnitsPerDevPixel = aFrame->PresContext()->AppUnitsPerDevPixel(); if (!prop || !prop->ReferencesValidResources()) { // The frame is either not there or not currently available, @@ -359,17 +359,17 @@ nsSVGIntegrationUtils::AdjustInvalidArea nsRect nsSVGIntegrationUtils::GetRequiredSourceForInvalidArea(nsIFrame* aFrame, const nsRect& aDirtyRect) { // Don't bother calling GetEffectProperties; the filter property should // already have been set up during reflow/ComputeFrameEffectsRect nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(aFrame); - nsSVGFilterProperty *prop = nsSVGEffects::GetFilterProperty(firstFrame); + nsSVGFilterProperty *prop = SVGObserverUtils::GetFilterProperty(firstFrame); if (!prop || !prop->ReferencesValidResources()) { return aDirtyRect; } // Convert aDirtyRect into "user space" in app units: nsPoint toUserSpace = aFrame->GetOffsetTo(firstFrame) + GetOffsetToBoundingBox(firstFrame); nsRect postEffectsRect = aDirtyRect + toUserSpace; @@ -716,18 +716,18 @@ MoveContextOriginToUserSpace(nsIFrame* a return offset; } bool nsSVGIntegrationUtils::IsMaskResourceReady(nsIFrame* aFrame) { nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(aFrame); - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(firstFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(firstFrame); nsTArray<nsSVGMaskFrame*> maskFrames = effectProperties.GetMaskFrames(); const nsStyleSVGReset* svgReset = firstFrame->StyleSVGReset(); for (uint32_t i = 0; i < maskFrames.Length(); i++) { // Refers to a valid SVG mask. if (maskFrames[i]) { continue; } @@ -771,18 +771,18 @@ nsSVGIntegrationUtils::PaintMask(const P nsIFrame* frame = aParams.frame; if (!ValidateSVGFrame(frame)) { return; } gfxContext& ctx = aParams.ctx; nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(frame); - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(firstFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(firstFrame); RefPtr<DrawTarget> maskTarget = ctx.GetDrawTarget(); if (maskUsage.shouldGenerateMaskLayer && (maskUsage.shouldGenerateClipMaskLayer || maskUsage.shouldApplyClipPath)) { // We will paint both mask of positioned mask and clip-path into // maskTarget. @@ -890,18 +890,18 @@ nsSVGIntegrationUtils::PaintMaskAndClipP gfxContext& context = aParams.ctx; gfxContextMatrixAutoSaveRestore matrixAutoSaveRestore(&context); /* Properties are added lazily and may have been removed by a restyle, so make sure all applicable ones are set again. */ nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(frame); - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(firstFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(firstFrame); nsSVGClipPathFrame *clipPathFrame = effectProperties.GetClipPathFrame(); gfxMatrix cssPxToDevPxMatrix = nsSVGUtils::GetCSSPxToDevPxMatrix(frame); nsTArray<nsSVGMaskFrame*> maskFrames = effectProperties.GetMaskFrames(); bool shouldGenerateMask = (maskUsage.opacity != 1.0f || maskUsage.shouldGenerateClipMaskLayer || @@ -1068,18 +1068,18 @@ nsSVGIntegrationUtils::PaintFilter(const if (opacity == 0.0f) { return; } /* Properties are added lazily and may have been removed by a restyle, so make sure all applicable ones are set again. */ nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(frame); - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(firstFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(firstFrame); if (effectProperties.HasInvalidFilter()) { return; } gfxContext& context = aParams.ctx; gfxContextAutoSaveRestore autoSR(&context);
--- a/layout/svg/nsSVGMarkerFrame.cpp +++ b/layout/svg/nsSVGMarkerFrame.cpp @@ -3,17 +3,17 @@ * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ // Main header first: #include "nsSVGMarkerFrame.h" // Keep others in (case-insensitive) order: #include "gfxContext.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "mozilla/dom/SVGMarkerElement.h" #include "SVGGeometryElement.h" #include "SVGGeometryFrame.h" using namespace mozilla::dom; using namespace mozilla::gfx; using namespace mozilla::image; @@ -37,17 +37,17 @@ nsSVGMarkerFrame::AttributeChanged(int32 (aAttribute == nsGkAtoms::markerUnits || aAttribute == nsGkAtoms::refX || aAttribute == nsGkAtoms::refY || aAttribute == nsGkAtoms::markerWidth || aAttribute == nsGkAtoms::markerHeight || aAttribute == nsGkAtoms::orient || aAttribute == nsGkAtoms::preserveAspectRatio || aAttribute == nsGkAtoms::viewBox)) { - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); } return nsSVGContainerFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType); } #ifdef DEBUG void
--- a/layout/svg/nsSVGMaskFrame.cpp +++ b/layout/svg/nsSVGMaskFrame.cpp @@ -7,17 +7,17 @@ #include "nsSVGMaskFrame.h" // Keep others in (case-insensitive) order: #include "AutoReferenceChainGuard.h" #include "gfx2DGlue.h" #include "gfxContext.h" #include "mozilla/gfx/2D.h" #include "mozilla/RefPtr.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "mozilla/dom/SVGMaskElement.h" using namespace mozilla; using namespace mozilla::dom; using namespace mozilla::gfx; using namespace mozilla::image; static LuminanceType @@ -186,17 +186,17 @@ nsSVGMaskFrame::AttributeChanged(int32_t { if (aNameSpaceID == kNameSpaceID_None && (aAttribute == nsGkAtoms::x || aAttribute == nsGkAtoms::y || aAttribute == nsGkAtoms::width || aAttribute == nsGkAtoms::height|| aAttribute == nsGkAtoms::maskUnits || aAttribute == nsGkAtoms::maskContentUnits)) { - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); } return nsSVGContainerFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType); } #ifdef DEBUG void
--- a/layout/svg/nsSVGPatternFrame.cpp +++ b/layout/svg/nsSVGPatternFrame.cpp @@ -13,17 +13,17 @@ #include "gfxMatrix.h" #include "gfxPattern.h" #include "gfxPlatform.h" #include "mozilla/gfx/2D.h" #include "nsContentUtils.h" #include "nsGkAtoms.h" #include "nsSVGDisplayableFrame.h" #include "nsStyleContext.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "SVGGeometryFrame.h" #include "mozilla/dom/SVGPatternElement.h" #include "nsSVGUtils.h" #include "nsSVGAnimatedTransformList.h" #include "SVGContentUtils.h" using namespace mozilla; using namespace mozilla::dom; @@ -56,27 +56,27 @@ nsSVGPatternFrame::AttributeChanged(int3 aAttribute == nsGkAtoms::patternContentUnits || aAttribute == nsGkAtoms::patternTransform || aAttribute == nsGkAtoms::x || aAttribute == nsGkAtoms::y || aAttribute == nsGkAtoms::width || aAttribute == nsGkAtoms::height || aAttribute == nsGkAtoms::preserveAspectRatio || aAttribute == nsGkAtoms::viewBox)) { - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); } if ((aNameSpaceID == kNameSpaceID_XLink || aNameSpaceID == kNameSpaceID_None) && aAttribute == nsGkAtoms::href) { // Blow away our reference, if any - DeleteProperty(nsSVGEffects::HrefAsPaintingProperty()); + DeleteProperty(SVGObserverUtils::HrefAsPaintingProperty()); mNoHRefURI = false; // And update whoever references us - nsSVGEffects::InvalidateDirectRenderingObservers(this); + SVGObserverUtils::InvalidateDirectRenderingObservers(this); } return nsSVGPaintServerFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType); } #ifdef DEBUG void @@ -572,17 +572,17 @@ nsSVGPatternFrame::GetLengthValue(uint32 // Private (helper) methods nsSVGPatternFrame * nsSVGPatternFrame::GetReferencedPattern() { if (mNoHRefURI) return nullptr; nsSVGPaintingProperty *property = - GetProperty(nsSVGEffects::HrefAsPaintingProperty()); + GetProperty(SVGObserverUtils::HrefAsPaintingProperty()); if (!property) { // Fetch our pattern element's href or xlink:href attribute SVGPatternElement *pattern = static_cast<SVGPatternElement *>(GetContent()); nsAutoString href; if (pattern->mStringAttributes[SVGPatternElement::HREF].IsExplicitlySet()) { pattern->mStringAttributes[SVGPatternElement::HREF] .GetAnimValue(href, pattern); @@ -598,18 +598,18 @@ nsSVGPatternFrame::GetReferencedPattern( // Convert href to an nsIURI nsCOMPtr<nsIURI> targetURI; nsCOMPtr<nsIURI> base = mContent->GetBaseURI(); nsContentUtils::NewURIWithDocumentCharset(getter_AddRefs(targetURI), href, mContent->GetUncomposedDoc(), base); property = - nsSVGEffects::GetPaintingProperty(targetURI, this, - nsSVGEffects::HrefAsPaintingProperty()); + SVGObserverUtils::GetPaintingProperty(targetURI, this, + SVGObserverUtils::HrefAsPaintingProperty()); if (!property) return nullptr; } nsIFrame *result = property->GetReferencedFrame(); if (!result) return nullptr;
--- a/layout/svg/nsSVGStopFrame.cpp +++ b/layout/svg/nsSVGStopFrame.cpp @@ -3,17 +3,17 @@ * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ // Keep in (case-insensitive) order: #include "nsContainerFrame.h" #include "nsFrame.h" #include "nsGkAtoms.h" #include "nsStyleContext.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" // This is a very simple frame whose only purpose is to capture style change // events and propagate them to the parent. Most of the heavy lifting is done // within the nsSVGGradientFrame, which is the parent for this frame class nsSVGStopFrame : public nsFrame { friend nsIFrame* @@ -80,17 +80,17 @@ nsSVGStopFrame::AttributeChanged(int32_t nsIAtom* aAttribute, int32_t aModType) { if (aNameSpaceID == kNameSpaceID_None && aAttribute == nsGkAtoms::offset) { MOZ_ASSERT(GetParent()->IsSVGLinearGradientFrame() || GetParent()->IsSVGRadialGradientFrame(), "Observers observe the gradient, so that's what we must invalidate"); - nsSVGEffects::InvalidateDirectRenderingObservers(GetParent()); + SVGObserverUtils::InvalidateDirectRenderingObservers(GetParent()); } return nsFrame::AttributeChanged(aNameSpaceID, aAttribute, aModType); } // ------------------------------------------------------------------------- // Public functions // -------------------------------------------------------------------------
--- a/layout/svg/nsSVGSwitchFrame.cpp +++ b/layout/svg/nsSVGSwitchFrame.cpp @@ -1,16 +1,16 @@ /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ /* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ // Keep in (case-insensitive) order: #include "gfxRect.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGGFrame.h" #include "mozilla/dom/SVGSwitchElement.h" #include "nsSVGUtils.h" using namespace mozilla::gfx; using namespace mozilla::image; class nsSVGSwitchFrame final : public nsSVGGFrame @@ -167,17 +167,17 @@ nsSVGSwitchFrame::ReflowSVG() // the initial reflow is currently underway. bool isFirstReflow = (mState & NS_FRAME_FIRST_REFLOW); bool outerSVGHasHadFirstReflow = (GetParent()->GetStateBits() & NS_FRAME_FIRST_REFLOW) == 0; if (outerSVGHasHadFirstReflow) { - mState &= ~NS_FRAME_FIRST_REFLOW; // tell our children + RemoveStateBits(NS_FRAME_FIRST_REFLOW); // tell our children } nsOverflowAreas overflowRects; nsIFrame *child = GetActiveChildFrame(); nsSVGDisplayableFrame* svgChild = do_QueryFrame(child); if (svgChild) { MOZ_ASSERT(!(child->GetStateBits() & NS_FRAME_IS_NONDISPLAY), @@ -189,25 +189,25 @@ nsSVGSwitchFrame::ReflowSVG() // frame list, and we're iterating over that list now anyway. ConsiderChildOverflow(overflowRects, child); } if (isFirstReflow) { // Make sure we have our filter property (if any) before calling // FinishAndStoreOverflow (subsequent filter changes are handled off // nsChangeHint_UpdateEffects): - nsSVGEffects::UpdateEffects(this); + SVGObserverUtils::UpdateEffects(this); } FinishAndStoreOverflow(overflowRects, mRect.Size()); // Remove state bits after FinishAndStoreOverflow so that it doesn't // invalidate on first reflow: - mState &= ~(NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | - NS_FRAME_HAS_DIRTY_CHILDREN); + RemoveStateBits(NS_FRAME_FIRST_REFLOW | NS_FRAME_IS_DIRTY | + NS_FRAME_HAS_DIRTY_CHILDREN); } SVGBBox nsSVGSwitchFrame::GetBBoxContribution(const Matrix &aToBBoxUserspace, uint32_t aFlags) { nsIFrame* kid = GetActiveChildFrame(); nsSVGDisplayableFrame* svgKid = do_QueryFrame(kid);
--- a/layout/svg/nsSVGUseFrame.cpp +++ b/layout/svg/nsSVGUseFrame.cpp @@ -2,17 +2,17 @@ /* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ #include "nsSVGUseFrame.h" #include "nsContentUtils.h" #include "mozilla/dom/SVGUseElement.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" using namespace mozilla::dom; //---------------------------------------------------------------------- // Implementation nsIFrame* NS_NewSVGUseFrame(nsIPresShell* aPresShell, nsStyleContext* aContext)
--- a/layout/svg/nsSVGUtils.cpp +++ b/layout/svg/nsSVGUtils.cpp @@ -31,17 +31,17 @@ #include "nsIPresShell.h" #include "nsSVGDisplayableFrame.h" #include "nsLayoutUtils.h" #include "nsPresContext.h" #include "nsStyleCoord.h" #include "nsStyleStruct.h" #include "nsSVGClipPathFrame.h" #include "nsSVGContainerFrame.h" -#include "nsSVGEffects.h" +#include "SVGObserverUtils.h" #include "nsSVGFilterPaintCallback.h" #include "nsSVGForeignObjectFrame.h" #include "nsSVGInnerSVGFrame.h" #include "nsSVGIntegrationUtils.h" #include "nsSVGLength2.h" #include "nsSVGMaskFrame.h" #include "nsSVGOuterSVGFrame.h" #include "mozilla/dom/SVGClipPathElement.h" @@ -150,17 +150,17 @@ nsSVGUtils::Init() nsRect nsSVGUtils::GetPostFilterVisualOverflowRect(nsIFrame *aFrame, const nsRect &aPreFilterRect) { MOZ_ASSERT(aFrame->GetStateBits() & NS_FRAME_SVG_LAYOUT, "Called on invalid frame type"); - nsSVGFilterProperty *property = nsSVGEffects::GetFilterProperty(aFrame); + nsSVGFilterProperty *property = SVGObserverUtils::GetFilterProperty(aFrame); if (!property || !property->ReferencesValidResources()) { return aPreFilterRect; } return nsFilterInstance::GetPostFilterBounds(aFrame, nullptr, &aPreFilterRect); } bool @@ -189,17 +189,17 @@ nsSVGUtils::ScheduleReflowSVG(nsIFrame * "Passed bad frame!"); // If this is triggered, the callers should be fixed to call us before // ReflowSVG is called. If we try to mark dirty bits on frames while we're // in the process of removing them, things will get messed up. NS_ASSERTION(!OuterSVGIsCallingReflowSVG(aFrame), "Do not call under nsSVGDisplayableFrame::ReflowSVG!"); - // We don't call nsSVGEffects::InvalidateRenderingObservers here because + // We don't call SVGObserverUtils::InvalidateRenderingObservers here because // we should only be called under InvalidateAndScheduleReflowSVG (which // calls InvalidateBounds) or nsSVGDisplayContainerFrame::InsertFrames // (at which point the frame has no observers). if (aFrame->GetStateBits() & NS_FRAME_IS_NONDISPLAY) { return; } @@ -269,17 +269,17 @@ nsSVGUtils::NotifyAncestorsOfFilterRegio "Not expecting to be called on the outer SVG Frame"); aFrame = aFrame->GetParent(); while (aFrame) { if (aFrame->GetStateBits() & NS_STATE_IS_OUTER_SVG) return; - nsSVGFilterProperty *property = nsSVGEffects::GetFilterProperty(aFrame); + nsSVGFilterProperty *property = SVGObserverUtils::GetFilterProperty(aFrame); if (property) { property->Invalidate(); } aFrame = aFrame->GetParent(); } } Size @@ -501,18 +501,18 @@ void nsSVGUtils::DetermineMaskUsage(nsIFrame* aFrame, bool aHandleOpacity, MaskUsage& aUsage) { aUsage.opacity = ComputeOpacity(aFrame, aHandleOpacity); nsIFrame* firstFrame = nsLayoutUtils::FirstContinuationOrIBSplitSibling(aFrame); - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(firstFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(firstFrame); const nsStyleSVGReset *svgReset = firstFrame->StyleSVGReset(); nsTArray<nsSVGMaskFrame*> maskFrames = effectProperties.GetMaskFrames(); #ifdef MOZ_ENABLE_MASK_AS_SHORTHAND aUsage.shouldGenerateMaskLayer = (maskFrames.Length() > 0); #else // Since we do not support image mask so far, we should treat any @@ -731,18 +731,18 @@ nsSVGUtils::PaintFrameWithEffects(nsIFra * + Use cairo's clipPath when representable natively (single object * clip region). *f * + Merge opacity and masking if both used together. */ /* Properties are added lazily and may have been removed by a restyle, so make sure all applicable ones are set again. */ - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(aFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(aFrame); if (effectProperties.HasInvalidEffects()) { // Some resource is invalid. We shouldn't paint anything. return; } nsSVGClipPathFrame *clipPathFrame = effectProperties.GetClipPathFrame(); nsTArray<nsSVGMaskFrame*> masks = effectProperties.GetMaskFrames(); nsSVGMaskFrame *maskFrame = masks.IsEmpty() ? nullptr : masks[0]; @@ -883,18 +883,18 @@ nsSVGUtils::PaintFrameWithEffects(nsIFra MOZ_ASSERT(target != &aContext); blender.BlendToTarget(); } } bool nsSVGUtils::HitTestClip(nsIFrame *aFrame, const gfxPoint &aPoint) { - nsSVGEffects::EffectProperties props = - nsSVGEffects::GetEffectProperties(aFrame); + SVGObserverUtils::EffectProperties props = + SVGObserverUtils::GetEffectProperties(aFrame); if (!props.mClipPath) { const nsStyleSVGReset *style = aFrame->StyleSVGReset(); if (style->HasClipPath()) { return nsCSSClipPathInstance::HitTestBasicShapeClip(aFrame, aPoint); } return true; } @@ -1173,18 +1173,18 @@ nsSVGUtils::GetBBox(nsIFrame* aFrame, ui bool hasClip = aFrame->StyleDisplay()->IsScrollableOverflow(); if (hasClip) { clipRect = nsSVGUtils::GetClipRectForFrame(aFrame, x, y, width, height); if (aFrame->IsSVGForeignObjectFrame() || aFrame->IsSVGUseFrame()) { clipRect = matrix.TransformBounds(clipRect); } } - nsSVGEffects::EffectProperties effectProperties = - nsSVGEffects::GetEffectProperties(aFrame); + SVGObserverUtils::EffectProperties effectProperties = + SVGObserverUtils::GetEffectProperties(aFrame); if (effectProperties.HasInvalidClipPath()) { bbox = gfxRect(0, 0, 0, 0); } else { nsSVGClipPathFrame *clipPathFrame = effectProperties.GetClipPathFrame(); if (clipPathFrame) { SVGClipPathElement *clipContent = static_cast<SVGClipPathElement*>(clipPathFrame->GetContent()); @@ -1501,18 +1501,18 @@ nsSVGUtils::MakeFillPatternFor(nsIFrame* // Combine the group opacity into the fill opacity (we will have skipped // creating an offscreen surface to apply the group opacity). fillOpacity *= opacity; } const DrawTarget* dt = aContext->GetDrawTarget(); nsSVGPaintServerFrame *ps = - nsSVGEffects::GetPaintServer(aFrame, &nsStyleSVG::mFill, - nsSVGEffects::FillProperty()); + SVGObserverUtils::GetPaintServer(aFrame, &nsStyleSVG::mFill, + SVGObserverUtils::FillProperty()); if (ps) { RefPtr<gfxPattern> pattern = ps->GetPaintServerPattern(aFrame, dt, aContext->CurrentMatrix(), &nsStyleSVG::mFill, fillOpacity, aImgParams); if (pattern) { pattern->CacheColorStops(dt); aOutPattern->Init(*pattern->GetPattern(dt)); @@ -1577,18 +1577,18 @@ nsSVGUtils::MakeStrokePatternFor(nsIFram // Combine the group opacity into the stroke opacity (we will have skipped // creating an offscreen surface to apply the group opacity). strokeOpacity *= opacity; } const DrawTarget* dt = aContext->GetDrawTarget(); nsSVGPaintServerFrame *ps = - nsSVGEffects::GetPaintServer(aFrame, &nsStyleSVG::mStroke, - nsSVGEffects::StrokeProperty()); + SVGObserverUtils::GetPaintServer(aFrame, &nsStyleSVG::mStroke, + SVGObserverUtils::StrokeProperty()); if (ps) { RefPtr<gfxPattern> pattern = ps->GetPaintServerPattern(aFrame, dt, aContext->CurrentMatrix(), &nsStyleSVG::mStroke, strokeOpacity, aImgParams); if (pattern) { pattern->CacheColorStops(dt); aOutPattern->Init(*pattern->GetPattern(dt));
--- a/layout/xul/nsBox.cpp +++ b/layout/xul/nsBox.cpp @@ -126,17 +126,17 @@ nsBox::BeginXULLayout(nsBoxLayoutState& XULDumpBox(stdout); printf("\n"); gIndent++; #endif // mark ourselves as dirty so no child under us // can post an incremental layout. // XXXldb Is this still needed? - mState |= NS_FRAME_HAS_DIRTY_CHILDREN; + AddStateBits(NS_FRAME_HAS_DIRTY_CHILDREN); if (GetStateBits() & NS_FRAME_IS_DIRTY) { // If the parent is dirty, all the children are dirty (ReflowInput // does this too). nsIFrame* box; for (box = GetChildXULBox(this); box; box = GetNextXULBox(box)) box->AddStateBits(NS_FRAME_IS_DIRTY);
--- a/layout/xul/nsBoxFrame.cpp +++ b/layout/xul/nsBoxFrame.cpp @@ -119,21 +119,20 @@ NS_QUERYFRAME_TAIL_INHERITING(nsContaine nsBoxFrame::nsBoxFrame(nsStyleContext* aContext, ClassID aID, bool aIsRoot, nsBoxLayout* aLayoutManager) : nsContainerFrame(aContext, aID) , mFlex(0) , mAscent(0) { - mState |= NS_STATE_IS_HORIZONTAL; - mState |= NS_STATE_AUTO_STRETCH; + AddStateBits(NS_STATE_IS_HORIZONTAL | NS_STATE_AUTO_STRETCH); if (aIsRoot) - mState |= NS_STATE_IS_ROOT; + AddStateBits(NS_STATE_IS_ROOT); mValign = vAlign_Top; mHalign = hAlign_Left; // if no layout manager specified us the static sprocket layout nsCOMPtr<nsBoxLayout> layout = aLayoutManager; if (layout == nullptr) { @@ -230,56 +229,56 @@ nsBoxFrame::CacheAttributes() */ mValign = vAlign_Top; mHalign = hAlign_Left; bool orient = false; GetInitialOrientation(orient); if (orient) - mState |= NS_STATE_IS_HORIZONTAL; + AddStateBits(NS_STATE_IS_HORIZONTAL); else - mState &= ~NS_STATE_IS_HORIZONTAL; + RemoveStateBits(NS_STATE_IS_HORIZONTAL); bool normal = true; GetInitialDirection(normal); if (normal) - mState |= NS_STATE_IS_DIRECTION_NORMAL; + AddStateBits(NS_STATE_IS_DIRECTION_NORMAL); else - mState &= ~NS_STATE_IS_DIRECTION_NORMAL; + RemoveStateBits(NS_STATE_IS_DIRECTION_NORMAL); GetInitialVAlignment(mValign); GetInitialHAlignment(mHalign); bool equalSize = false; GetInitialEqualSize(equalSize); if (equalSize) - mState |= NS_STATE_EQUAL_SIZE; + AddStateBits(NS_STATE_EQUAL_SIZE); else - mState &= ~NS_STATE_EQUAL_SIZE; + RemoveStateBits(NS_STATE_EQUAL_SIZE); bool autostretch = !!(mState & NS_STATE_AUTO_STRETCH); GetInitialAutoStretch(autostretch); if (autostretch) - mState |= NS_STATE_AUTO_STRETCH; + AddStateBits(NS_STATE_AUTO_STRETCH); else - mState &= ~NS_STATE_AUTO_STRETCH; + RemoveStateBits(NS_STATE_AUTO_STRETCH); #ifdef DEBUG_LAYOUT bool debug = mState & NS_STATE_SET_TO_DEBUG; bool debugSet = GetInitialDebug(debug); if (debugSet) { - mState |= NS_STATE_DEBUG_WAS_SET; + AddStateBits(NS_STATE_DEBUG_WAS_SET); if (debug) - mState |= NS_STATE_SET_TO_DEBUG; + AddStateBits(NS_STATE_SET_TO_DEBUG); else - mState &= ~NS_STATE_SET_TO_DEBUG; + RemoveStateBits(NS_STATE_SET_TO_DEBUG); } else { - mState &= ~NS_STATE_DEBUG_WAS_SET; + RemoveStateBits(NS_STATE_DEBUG_WAS_SET); } #endif } #ifdef DEBUG_LAYOUT bool nsBoxFrame::GetInitialDebug(bool& aDebug) { @@ -561,17 +560,17 @@ nsBoxFrame::GetInitialAutoStretch(bool& void nsBoxFrame::DidReflow(nsPresContext* aPresContext, const ReflowInput* aReflowInput, nsDidReflowStatus aStatus) { nsFrameState preserveBits = mState & (NS_FRAME_IS_DIRTY | NS_FRAME_HAS_DIRTY_CHILDREN); nsFrame::DidReflow(aPresContext, aReflowInput, aStatus); - mState |= preserveBits; + AddStateBits(preserveBits); } bool nsBoxFrame::HonorPrintBackgroundSettings() { return (!mContent || !mContent->IsInNativeAnonymousSubtree()) && nsContainerFrame::HonorPrintBackgroundSettings(); } @@ -975,19 +974,19 @@ nsBoxFrame::SetXULDebug(nsBoxLayoutState // see if our state matches the given debug state bool debugSet = mState & NS_STATE_CURRENTLY_IN_DEBUG; bool debugChanged = (!aDebug && debugSet) || (aDebug && !debugSet); // if it doesn't then tell each child below us the new debug state if (debugChanged) { if (aDebug) { - mState |= NS_STATE_CURRENTLY_IN_DEBUG; + AddStateBits(NS_STATE_CURRENTLY_IN_DEBUG); } else { - mState &= ~NS_STATE_CURRENTLY_IN_DEBUG; + RemoveStateBits(NS_STATE_CURRENTLY_IN_DEBUG); } SetDebugOnChildList(aState, mFirstChild, aDebug); MarkIntrinsicISizesDirty(); } return NS_OK; @@ -1169,66 +1168,66 @@ nsBoxFrame::AttributeChanged(int32_t aNa aAttribute == nsGkAtoms::dir) { mValign = nsBoxFrame::vAlign_Top; mHalign = nsBoxFrame::hAlign_Left; bool orient = true; GetInitialOrientation(orient); if (orient) - mState |= NS_STATE_IS_HORIZONTAL; + AddStateBits(NS_STATE_IS_HORIZONTAL); else - mState &= ~NS_STATE_IS_HORIZONTAL; + RemoveStateBits(NS_STATE_IS_HORIZONTAL); bool normal = true; GetInitialDirection(normal); if (normal) - mState |= NS_STATE_IS_DIRECTION_NORMAL; + AddStateBits(NS_STATE_IS_DIRECTION_NORMAL); else - mState &= ~NS_STATE_IS_DIRECTION_NORMAL; + RemoveStateBits(NS_STATE_IS_DIRECTION_NORMAL); GetInitialVAlignment(mValign); GetInitialHAlignment(mHalign); bool equalSize = false; GetInitialEqualSize(equalSize); if (equalSize) - mState |= NS_STATE_EQUAL_SIZE; + AddStateBits(NS_STATE_EQUAL_SIZE); else - mState &= ~NS_STATE_EQUAL_SIZE; + RemoveStateBits(NS_STATE_EQUAL_SIZE); #ifdef DEBUG_LAYOUT bool debug = mState & NS_STATE_SET_TO_DEBUG; bool debugSet = GetInitialDebug(debug); if (debugSet) { - mState |= NS_STATE_DEBUG_WAS_SET; + AddStateBits(NS_STATE_DEBUG_WAS_SET); if (debug) - mState |= NS_STATE_SET_TO_DEBUG; + AddStateBits(NS_STATE_SET_TO_DEBUG); else - mState &= ~NS_STATE_SET_TO_DEBUG; + RemoveStateBits(NS_STATE_SET_TO_DEBUG); } else { - mState &= ~NS_STATE_DEBUG_WAS_SET; + RemoveStateBits(NS_STATE_DEBUG_WAS_SET); } #endif bool autostretch = !!(mState & NS_STATE_AUTO_STRETCH); GetInitialAutoStretch(autostretch); if (autostretch) - mState |= NS_STATE_AUTO_STRETCH; + AddStateBits(NS_STATE_AUTO_STRETCH); else - mState &= ~NS_STATE_AUTO_STRETCH; + RemoveStateBits(NS_STATE_AUTO_STRETCH); } else if (aAttribute == nsGkAtoms::left || aAttribute == nsGkAtoms::top || aAttribute == nsGkAtoms::right || aAttribute == nsGkAtoms::bottom || aAttribute == nsGkAtoms::start || aAttribute == nsGkAtoms::end) { - mState &= ~NS_STATE_STACK_NOT_POSITIONED; + RemoveStateBits(NS_STATE_STACK_NOT_POSITIONED); } else if (aAttribute == nsGkAtoms::mousethrough) { UpdateMouseThrough(); } PresContext()->PresShell()-> FrameNeedsReflow(this, nsIPresShell::eStyleChange, NS_FRAME_IS_DIRTY); }
--- a/layout/xul/nsScrollbarFrame.cpp +++ b/layout/xul/nsScrollbarFrame.cpp @@ -46,17 +46,17 @@ nsScrollbarFrame::Init(nsIContent* nsIFrame* aPrevInFlow) { nsBoxFrame::Init(aContent, aParent, aPrevInFlow); // We want to be a reflow root since we use reflows to move the // slider. Any reflow inside the scrollbar frame will be a reflow to // move the slider and will thus not change anything outside of the // scrollbar or change the size of the scrollbar frame. - mState |= NS_FRAME_REFLOW_ROOT; + AddStateBits(NS_FRAME_REFLOW_ROOT); } void nsScrollbarFrame::Reflow(nsPresContext* aPresContext, ReflowOutput& aDesiredSize, const ReflowInput& aReflowInput, nsReflowStatus& aStatus) {
--- a/layout/xul/nsSliderFrame.cpp +++ b/layout/xul/nsSliderFrame.cpp @@ -1527,19 +1527,19 @@ nsSliderFrame::GetXULMaxSize(nsBoxLayout void nsSliderFrame::EnsureOrient() { nsIFrame* scrollbarBox = GetScrollbar(); bool isHorizontal = (scrollbarBox->GetStateBits() & NS_STATE_IS_HORIZONTAL) != 0; if (isHorizontal) - mState |= NS_STATE_IS_HORIZONTAL; + AddStateBits(NS_STATE_IS_HORIZONTAL); else - mState &= ~NS_STATE_IS_HORIZONTAL; + RemoveStateBits(NS_STATE_IS_HORIZONTAL); } void nsSliderFrame::Notify(void) { bool stop = false;
--- a/layout/xul/nsSplitterFrame.cpp +++ b/layout/xul/nsSplitterFrame.cpp @@ -879,19 +879,19 @@ nsSplitterFrameInner::UpdateState() mState = newState; } void nsSplitterFrameInner::EnsureOrient() { bool isHorizontal = !(mParentBox->GetStateBits() & NS_STATE_IS_HORIZONTAL); if (isHorizontal) - mOuter->mState |= NS_STATE_IS_HORIZONTAL; + mOuter->AddStateBits(NS_STATE_IS_HORIZONTAL); else - mOuter->mState &= ~NS_STATE_IS_HORIZONTAL; + mOuter->RemoveStateBits(NS_STATE_IS_HORIZONTAL); } void nsSplitterFrameInner::AdjustChildren(nsPresContext* aPresContext) { EnsureOrient(); bool isHorizontal = !mOuter->IsXULHorizontal();
--- a/layout/xul/nsTextBoxFrame.cpp +++ b/layout/xul/nsTextBoxFrame.cpp @@ -640,17 +640,17 @@ nsTextBoxFrame::CalculateTitleForWidth(g // see if the text will completely fit in the width given nscoord titleWidth = nsLayoutUtils::AppUnitWidthOfStringBidi(mTitle, this, *fm, aRenderingContext); if (titleWidth <= aWidth) { mCroppedTitle = mTitle; if (HasRTLChars(mTitle) || StyleVisibility()->mDirection == NS_STYLE_DIRECTION_RTL) { - mState |= NS_FRAME_IS_BIDI; + AddStateBits(NS_FRAME_IS_BIDI); } return titleWidth; // fits, done. } const nsDependentString& kEllipsis = nsContentUtils::GetLocalizedEllipsis(); if (mCropType != CropNone) { // start with an ellipsis mCroppedTitle.Assign(kEllipsis); @@ -699,17 +699,17 @@ nsTextBoxFrame::CalculateTitleForWidth(g charWidth = nsLayoutUtils::AppUnitWidthOfString(pos, length, *fm, drawTarget); if (totalWidth + charWidth > aWidth) { break; } if (UCS2_CHAR_IS_BIDI(*pos)) { - mState |= NS_FRAME_IS_BIDI; + AddStateBits(NS_FRAME_IS_BIDI); } pos = nextPos; totalWidth += charWidth; } if (pos == dataBegin) { return titleWidth; } @@ -736,17 +736,17 @@ nsTextBoxFrame::CalculateTitleForWidth(g charWidth = nsLayoutUtils::AppUnitWidthOfString(pos, length, *fm, drawTarget); if (totalWidth + charWidth > aWidth) { break; } if (UCS2_CHAR_IS_BIDI(*pos)) { - mState |= NS_FRAME_IS_BIDI; + AddStateBits(NS_FRAME_IS_BIDI); } prevPos = pos; totalWidth += charWidth; } if (prevPos == dataEnd) { return titleWidth; } @@ -788,17 +788,17 @@ nsTextBoxFrame::CalculateTitleForWidth(g charWidth = nsLayoutUtils::AppUnitWidthOfString(leftPos, length, *fm, drawTarget); if (totalWidth + charWidth > aWidth) { break; } if (UCS2_CHAR_IS_BIDI(*leftPos)) { - mState |= NS_FRAME_IS_BIDI; + AddStateBits(NS_FRAME_IS_BIDI); } leftString.Append(leftPos, length); leftPos = pos; totalWidth += charWidth; if (leftPos >= rightPos) { break; @@ -810,17 +810,17 @@ nsTextBoxFrame::CalculateTitleForWidth(g charWidth = nsLayoutUtils::AppUnitWidthOfString(pos, length, *fm, drawTarget); if (totalWidth + charWidth > aWidth) { break; } if (UCS2_CHAR_IS_BIDI(*pos)) { - mState |= NS_FRAME_IS_BIDI; + AddStateBits(NS_FRAME_IS_BIDI); } rightString.Insert(pos, 0, length); rightPos = pos; totalWidth += charWidth; } mCroppedTitle = leftString + kEllipsis + rightString;
--- a/memory/build/mozjemalloc.cpp +++ b/memory/build/mozjemalloc.cpp @@ -4685,27 +4685,16 @@ MozJemalloc::malloc(size_t aSize) RETURN: if (!ret) { errno = ENOMEM; } return ret; } -/* - * In ELF systems the default visibility allows symbols to be preempted at - * runtime. This in turn prevents the uses of memalign in this file from being - * optimized. What we do in here is define two aliasing symbols (they point to - * the same code): memalign and memalign_internal. The internal version has - * hidden visibility and is used in every reference from this file. - * - * For more information on this technique, see section 2.2.7 (Avoid Using - * Exported Symbols) in http://www.akkadia.org/drepper/dsohowto.pdf. - */ - template<> inline void* MozJemalloc::memalign(size_t aAlignment, size_t aSize) { void* ret; MOZ_ASSERT(((aAlignment - 1) & aAlignment) == 0); if (malloc_init()) {
--- a/mobile/android/geckoview/src/main/java/org/mozilla/gecko/GeckoViewSettings.java +++ b/mobile/android/geckoview/src/main/java/org/mozilla/gecko/GeckoViewSettings.java @@ -57,18 +57,18 @@ public final class GeckoViewSettings { * active GeckoView session will be ignored. */ public static final Key<Boolean> USE_MULTIPROCESS = new Key<Boolean>("useMultiprocess"); /* * Key to specify which display-mode we should use */ - public static final Key<Boolean> DISPLAY_MODE = - new Key<Boolean>("displayMode"); + public static final Key<Integer> DISPLAY_MODE = + new Key<Integer>("displayMode"); private final EventDispatcher mEventDispatcher; private final GeckoBundle mBundle; public GeckoViewSettings() { this(null); } @@ -100,28 +100,28 @@ public final class GeckoViewSettings { } public boolean getBoolean(final Key<Boolean> key) { synchronized (mBundle) { return mBundle.getBoolean(key.text); } } - public void setInt(final Key<Boolean> key, int value) { + public void setInt(final Key<Integer> key, int value) { synchronized (mBundle) { final Object old = mBundle.get(key.text); if (old != null && old.equals(value)) { return; } mBundle.putInt(key.text, value); } dispatchUpdate(); } - public int getInt(final Key<Boolean> key) { + public int getInt(final Key<Integer> key) { synchronized (mBundle) { return mBundle.getInt(key.text); } } /* package */ GeckoBundle asBundle() { return mBundle; }
--- a/netwerk/dns/nsDNSService2.cpp +++ b/netwerk/dns/nsDNSService2.cpp @@ -987,16 +987,39 @@ nsDNSService::Resolve(const nsACString } NS_IMETHODIMP nsDNSService::ResolveNative(const nsACString &aHostname, uint32_t flags, const OriginAttributes &aOriginAttributes, nsIDNSRecord **result) { + // Synchronous resolution is not available on the main thread. + if (NS_IsMainThread()) { + return NS_ERROR_NOT_AVAILABLE; + } + + return ResolveInternal(aHostname, flags, aOriginAttributes, result); +} + +nsresult +nsDNSService::DeprecatedSyncResolve(const nsACString &aHostname, + uint32_t flags, + const OriginAttributes &aOriginAttributes, + nsIDNSRecord **result) +{ + return ResolveInternal(aHostname, flags, aOriginAttributes, result); +} + +nsresult +nsDNSService::ResolveInternal(const nsACString &aHostname, + uint32_t flags, + const OriginAttributes &aOriginAttributes, + nsIDNSRecord **result) +{ // grab reference to global host resolver and IDN service. beware // simultaneous shutdown!! RefPtr<nsHostResolver> res; nsCOMPtr<nsIIDNService> idn; bool localDomain = false; { MutexAutoLock lock(mLock); res = mResolver;
--- a/netwerk/dns/nsDNSService2.h +++ b/netwerk/dns/nsDNSService2.h @@ -14,16 +14,18 @@ #include "nsHostResolver.h" #include "nsAutoPtr.h" #include "nsString.h" #include "nsTHashtable.h" #include "nsHashKeys.h" #include "mozilla/Mutex.h" #include "mozilla/Attributes.h" +class nsAuthSSPI; + class nsDNSService final : public nsPIDNSService , public nsIObserver , public nsIMemoryReporter { public: NS_DECL_THREADSAFE_ISUPPORTS NS_DECL_NSPIDNSSERVICE NS_DECL_NSIDNSSERVICE @@ -33,28 +35,41 @@ public: nsDNSService(); static nsIDNSService* GetXPCOMSingleton(); size_t SizeOfIncludingThis(mozilla::MallocSizeOf mallocSizeOf) const; bool GetOffline() const; +protected: + friend class nsAuthSSPI; + + nsresult DeprecatedSyncResolve(const nsACString &aHostname, + uint32_t flags, + const mozilla::OriginAttributes &aOriginAttributes, + nsIDNSRecord **result); + private: ~nsDNSService(); static nsDNSService* GetSingleton(); uint16_t GetAFForLookup(const nsACString &host, uint32_t flags); nsresult PreprocessHostname(bool aLocalDomain, const nsACString &aInput, nsIIDNService *aIDN, nsACString &aACE); + nsresult ResolveInternal(const nsACString &aHostname, + uint32_t flags, + const mozilla::OriginAttributes &aOriginAttributes, + nsIDNSRecord **result); + RefPtr<nsHostResolver> mResolver; nsCOMPtr<nsIIDNService> mIDN; // mLock protects access to mResolver and mIPv4OnlyDomains mozilla::Mutex mLock; // mIPv4OnlyDomains is a comma-separated list of domains for which only // IPv4 DNS lookups are performed. This allows the user to disable IPv6 on
--- a/netwerk/dns/nsIDNSService.idl +++ b/netwerk/dns/nsIDNSService.idl @@ -94,31 +94,33 @@ interface nsIDNSService : nsISupports [notxpcom] nsresult cancelAsyncResolveNative(in AUTF8String aHostName, in unsigned long aFlags, in nsIDNSListener aListener, in nsresult aReason, in OriginAttributes aOriginAttributes); /** - * called to synchronously resolve a hostname. warning this method may - * block the calling thread for a long period of time. it is extremely - * unwise to call this function on the UI thread of an application. + * called to synchronously resolve a hostname. + * + * Since this method may block the calling thread for a long period of + * time, it may not be accessed from the main thread. * * @param aHostName * the hostname or IP-address-literal to resolve. * @param aFlags * a bitwise OR of the RESOLVE_ prefixed constants defined below. * @param aOriginAttributes * the originAttribute for this resolving, the DNS cache will be * separated according to this originAttributes. This attribute is * optional to avoid breaking add-ons. * * @return DNS record corresponding to the given hostname. * @throws NS_ERROR_UNKNOWN_HOST if host could not be resolved. + * @throws NS_ERROR_NOT_AVAILABLE if accessed from the main thread. */ [implicit_jscontext, optional_argc] nsIDNSRecord resolve(in AUTF8String aHostName, in unsigned long aFlags, [optional] in jsval aOriginAttributes); [notxpcom] nsresult resolveNative(in AUTF8String aHostName,
--- a/security/nss/automation/release/nspr-version.txt +++ b/security/nss/automation/release/nspr-version.txt @@ -1,9 +1,9 @@ -4.15 +4.17 # The first line of this file must contain the human readable NSPR # version number, which is the minimum required version of NSPR # that is supported by this version of NSS. # # This information is used by release automation, # when creating an NSS source archive. #
--- a/security/nss/coreconf/coreconf.dep +++ b/security/nss/coreconf/coreconf.dep @@ -5,9 +5,8 @@ /* * A dummy header file that is a dependency for all the object files. * Used to force a full recompilation of NSS in Mozilla's Tinderbox * depend builds. See comments in rules.mk. */ #error "Do not include this header file." -
--- a/security/nss/lib/nss/nss.h +++ b/security/nss/lib/nss/nss.h @@ -17,22 +17,22 @@ /* * NSS's major version, minor version, patch level, build number, and whether * this is a beta release. * * The format of the version string should be * "<major version>.<minor version>[.<patch level>[.<build number>]][ <ECC>][ <Beta>]" */ -#define NSS_VERSION "3.33" _NSS_CUSTOMIZED " Beta" +#define NSS_VERSION "3.33" _NSS_CUSTOMIZED #define NSS_VMAJOR 3 #define NSS_VMINOR 33 #define NSS_VPATCH 0 #define NSS_VBUILD 0 -#define NSS_BETA PR_TRUE +#define NSS_BETA PR_FALSE #ifndef RC_INVOKED #include "seccomon.h" typedef struct NSSInitParametersStr NSSInitParameters; /*
--- a/security/nss/lib/softoken/softkver.h +++ b/security/nss/lib/softoken/softkver.h @@ -12,16 +12,16 @@ /* * Softoken's major version, minor version, patch level, build number, * and whether this is a beta release. * * The format of the version string should be * "<major version>.<minor version>[.<patch level>[.<build number>]][ <ECC>][ <Beta>]" */ -#define SOFTOKEN_VERSION "3.33" SOFTOKEN_ECC_STRING " Beta" +#define SOFTOKEN_VERSION "3.33" SOFTOKEN_ECC_STRING #define SOFTOKEN_VMAJOR 3 #define SOFTOKEN_VMINOR 33 #define SOFTOKEN_VPATCH 0 #define SOFTOKEN_VBUILD 0 -#define SOFTOKEN_BETA PR_TRUE +#define SOFTOKEN_BETA PR_FALSE #endif /* _SOFTKVER_H_ */
--- a/security/nss/lib/util/nssutil.h +++ b/security/nss/lib/util/nssutil.h @@ -14,22 +14,22 @@ /* * NSS utilities's major version, minor version, patch level, build number, * and whether this is a beta release. * * The format of the version string should be * "<major version>.<minor version>[.<patch level>[.<build number>]][ <Beta>]" */ -#define NSSUTIL_VERSION "3.33 Beta" +#define NSSUTIL_VERSION "3.33" #define NSSUTIL_VMAJOR 3 #define NSSUTIL_VMINOR 33 #define NSSUTIL_VPATCH 0 #define NSSUTIL_VBUILD 0 -#define NSSUTIL_BETA PR_TRUE +#define NSSUTIL_BETA PR_FALSE SEC_BEGIN_PROTOS /* * Returns a const string of the UTIL library version. */ extern const char *NSSUTIL_GetVersion(void);
--- a/uriloader/exthandler/nsHandlerService-json.js +++ b/uriloader/exthandler/nsHandlerService-json.js @@ -266,17 +266,39 @@ HandlerService.prototype = { enumerate() { let handlers = Cc["@mozilla.org/array;1"] .createInstance(Ci.nsIMutableArray); for (let type of Object.keys(this._store.data.mimeTypes)) { let handler = gMIMEService.getFromTypeAndExtension(type, null); handlers.appendElement(handler); } for (let type of Object.keys(this._store.data.schemes)) { - let handler = gExternalProtocolService.getProtocolHandlerInfo(type); + // nsIExternalProtocolService.getProtocolHandlerInfo can be expensive + // on Windows, so we return a proxy to delay retrieving the nsIHandlerInfo + // until one of its properties is accessed. + // + // Note: our caller still needs to yield periodically when iterating + // the enumerator and accessing handler properties to avoid monopolizing + // the main thread. + // + let handler = new Proxy( + { + QueryInterface: XPCOMUtils.generateQI([Ci.nsIHandlerInfo]), + type: type, + get _handlerInfo() { + delete this._handlerInfo; + return this._handlerInfo = gExternalProtocolService.getProtocolHandlerInfo(type); + }, + }, + { + get: function(target, name) { + return target[name] || target._handlerInfo[name]; + }, + }, + ); handlers.appendElement(handler); } return handlers.enumerate(); }, // nsIHandlerService store(handlerInfo) { let handlerList = this._getHandlerListByHandlerInfoType(handlerInfo);
--- a/widget/cocoa/nsCocoaWindow.mm +++ b/widget/cocoa/nsCocoaWindow.mm @@ -87,16 +87,17 @@ enum NSWindowOcclusionState { enum NSWindowTitleVisibility { NSWindowTitleVisible = 0, NSWindowTitleHidden = 1 }; @interface NSWindow(TitleVisibility) - (void)setTitleVisibility:(NSWindowTitleVisibility)visibility; +- (void)setTitlebarAppearsTransparent:(BOOL)isTitlebarTransparent; @end #endif #if !defined(MAC_OS_X_VERSION_10_12) || \ MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_12 @interface NSWindow(AutomaticWindowTabbing) @@ -485,16 +486,20 @@ nsresult nsCocoaWindow::CreateNativeWind // Create the window mWindow = [[windowClass alloc] initWithContentRect:contentRect styleMask:features backing:NSBackingStoreBuffered defer:YES]; if ([mWindow respondsToSelector:@selector(setTitleVisibility)]) { // By default, hide window titles. [mWindow setTitleVisibility:NSWindowTitleHidden]; } + if ([mWindow respondsToSelector:@selector(setTitlebarAppearsTransparent)]) { + // By default, hide window titlebars. + [mWindow setTitlebarAppearsTransparent:YES]; + } // setup our notification delegate. Note that setDelegate: does NOT retain. mDelegate = [[WindowDelegate alloc] initWithGeckoWindow:this]; [mWindow setDelegate:mDelegate]; // Make sure that the content rect we gave has been honored. NSRect wantedFrame = [mWindow frameRectForContentRect:contentRect]; if (!NSEqualRects([mWindow frame], wantedFrame)) { @@ -3152,16 +3157,19 @@ static const NSString* kStateCollectionB mDrawsIntoWindowFrame = aState; if (changed) { [self updateContentViewSize]; [self reflowTitlebarElements]; if ([self respondsToSelector:@selector(setTitleVisibility)]) { [self setTitleVisibility:mDrawsIntoWindowFrame ? NSWindowTitleHidden : NSWindowTitleVisible]; } + if ([self respondsToSelector:@selector(setTitlebarAppearsTransparent)]) { + [self setTitlebarAppearsTransparent:mDrawsIntoWindowFrame]; + } } } - (BOOL)drawsContentsIntoWindowFrame { return mDrawsIntoWindowFrame; }