Bug 97910

Summary: [SVG] Use references are much slower than necessary
Product: WebKit Reporter: Branimir Lambov <blambov>
Component: SVGAssignee: Florin Malita <fmalita>
Status: NEW ---    
Severity: Normal CC: fmalita, pdr, schenney, zimmermann
Priority: P2    
Version: 528+ (Nightly build)   
Hardware: Unspecified   
OS: Unspecified   
Description Flags
Example setting href attribute
Example creating new 'use' element
Example without changing reference, demonstrating what the performance should be none

Description Branimir Lambov 2012-09-28 07:12:50 PDT
Created attachment 166245 [details]
Example setting href attribute

The attached files contain a hierarchy of 'use' elements to build a graphic containing a few hundred triangles. It is not a problem for Chrome to render the graphic fluidly (use-levels-move), but if a new 'use' element references the graphic (use-levels-new-use), or the element's 'href' is changed (use-levels-set-href), the performance falls dramatically.

WebKit is copying the elements referenced by 'use', which should not be necessary at all. In other tests we have seen that it is actually faster to explicitly recreate referenced nodes with JavaScript than to refer to them with 'use' elements.

Opera does not have this problem, and runs all these examples at ~50 fps.
Comment 1 Branimir Lambov 2012-09-28 07:13:24 PDT
Created attachment 166246 [details]
Example creating new 'use' element
Comment 2 Branimir Lambov 2012-09-28 07:15:50 PDT
Created attachment 166247 [details]
Example without changing reference, demonstrating what the performance should be
Comment 3 Florin Malita 2012-09-28 07:57:34 PDT
(In reply to comment #0)
> WebKit is copying the elements referenced by 'use', which should not be necessary at all.

Deep cloning is likely needed to support full <use> semantics - see http://www.w3.org/TR/SVG/struct.html#UseElement

But the profile for the slow tests does seem odd - most cycles wasted in synchronization and string manipulation code:

  2.77%           chrome  libpthread-2.15.so                  [.] pthread_mutex_unlock
  2.59%           chrome  libpthread-2.15.so                  [.] pthread_mutex_lock
  1.36%          swapper  [kernel.kallsyms]                   [k] mwait_idle_with_hints
  1.35%           chrome  libwebkit.so                        [.] WTF::StringHasher::addCharactersToHash(unsigned short, unsigned short)
  1.25%           chrome  libwebkit.so                        [.] WTF::intHash(unsigned long)
  1.10%           chrome  libwebkit.so                        [.] WTF::OwnPtr<WTF::Mutex>::operator*() const
  1.05%           chrome  libwebkit.so                        [.] WTF::Locker<WTF::Mutex>::Locker(WTF::Mutex&)
  0.96%           chrome  libwebkit.so                        [.] WTF::Mutex::lock()
  0.94%           chrome  libwebkit.so                        [.] WebCore::Node::getFlag(WebCore::Node::NodeFlags) const
  0.79%           chrome  libwebkit.so                        [.] WTF::ThreadRestrictionVerifier::isSafeToUse() const
  0.76%           chrome  libwebkit.so                        [.] WTF::RefPtr<WTF::StringImpl>::get() const
  0.73%           chrome  chrome                              [.] (anonymous namespace)::FL_Previous_No_Check(void*)
  0.71%           chrome  libwebkit.so                        [.] unsigned int WTF::StringHasher::computeHashAndMaskTop8Bits<unsigned short, &(WTF::StringHasher::defaultConverter(unsi
  0.63%           chrome  libpthread-2.15.so                  [.] pthread_getspecific
  0.58%           chrome  chrome                              [.] PackedCache<36, unsigned long>::GetOrDefault(unsigned long, unsigned long) const
  0.57%           chrome  libwebkit.so                        [.] WebCore::Node::document() const
  0.50%           chrome  chrome                              [.] TCMalloc_PageMap3<36>::get(unsigned long) const
  0.50%           chrome  libwebkit.so                        [.] bool WTF::IdentityHashTranslator<WTF::PtrHash<WebCore::SVGElement*> >::equal<WebCore::SVGElement*>(WebCore::SVGElemen
  0.48%           chrome  libwebkit.so                        [.] WTF::Mutex::unlock()
  0.47%         cinnamon  [kernel.kallsyms]                   [k] audit_filter_syscall
  0.46%           chrome  libwebkit.so                        [.] WTF::ThreadIdentifierData::identifier()
  0.44%           chrome  libc-2.15.so                        [.] __memset_sse2
  0.44%           chrome  chrome                              [.] base::subtle::Acquire_Load(long const volatile*)
  0.44%           chrome  chrome (deleted)                    [.] 0x3255b0f
  0.39%           chrome  libwebkit.so                        [.] WTF::String::impl() const
  0.38%           chrome  libwebkit.so                        [.] WTF::Locker<WTF::Mutex>::~Locker()
  0.37%           chrome  libwebkit.so                        [.] void WTF::addIterator<WebCore::SVGElement*, WTF::KeyValuePair<WebCore::SVGElement*, WTF::OwnPtr<WTF::HashSet<WebCore:
  0.37%           chrome  libwebkit.so                        [.] WTF::RefCountedBase::derefBase()
  0.35%           chrome  chrome                              [.] CheckCachedSizeClass(void*)
  0.32%           chrome  libwebkit.so                        [.] WebCore::RenderObject::document() const
  0.32%           chrome  chrome                              [.] (anonymous namespace)::MaskPtr(void*)
  0.32%           chrome  libwebkit.so                        [.] WTF::StringHasher::defaultConverter(unsigned short)
  0.31%           chrome  libwebkit.so                        [.] WTF::doubleHash(unsigned int)
  0.31%           chrome  libwebkit.so                        [.] WTF::RefCountedBase::ref()
  0.28%           chrome  libwebkit.so                        [.] void WTF::removeIterator<WebCore::SVGElement*, WTF::KeyValuePair<WebCore::SVGElement*, WTF::OwnPtr<WTF::HashSet<WebCo
  0.27%           chrome  libwebkit.so                        [.] WTF::currentThread()
  0.27%           chrome  libwebkit.so                        [.] WTF::StringHasher::avalancheBits() const
Comment 4 Nikolas Zimmermann 2012-10-01 01:12:23 PDT
See 97905 comment #4 for a way out of this mess.