Commit a8b3cb0b authored by shans's avatar shans Committed by Commit bot

Correctly filter duplicate variable references in styles.

This patch introduces a HashSet to track custom property additions
when constructing PropertySets, so that duplicates are excluded.
This already happens for standard properties, but is tracked for
them by a BitArray.

Review URL: https://codereview.chromium.org/1709843002

Cr-Commit-Position: refs/heads/master@{#376134}
parent cda4afd7
<!DOCTYPE html>
<script src="../../../resources/testharness.js"></script>
<script src="../../../resources/testharnessreport.js"></script>
<div id='testElem'></div>
<script>
test(function() {
testElem.setAttribute('style', '--foo:one;--foo:two;');
assert_equals(testElem.style.length, 1);
assert_equals(testElem.style.getPropertyValue('--foo'), 'two');
}, "the cascade applies correctly to variables in inline style.")
</script>
......@@ -61,7 +61,7 @@ bool CSSParserImpl::parseVariableValue(MutableStylePropertySet* declaration, con
return declaration->addParsedProperties(parser.m_parsedProperties);
}
static inline void filterProperties(bool important, const WillBeHeapVector<CSSProperty, 256>& input, WillBeHeapVector<CSSProperty, 256>& output, size_t& unusedEntries, BitArray<numCSSProperties>& seenProperties)
static inline void filterProperties(bool important, const WillBeHeapVector<CSSProperty, 256>& input, WillBeHeapVector<CSSProperty, 256>& output, size_t& unusedEntries, BitArray<numCSSProperties>& seenProperties, HashSet<AtomicString>& seenCustomProperties)
{
// Add properties in reverse order so that highest priority definitions are reached first. Duplicate definitions can then be ignored when found.
for (size_t i = input.size(); i--; ) {
......@@ -69,8 +69,13 @@ static inline void filterProperties(bool important, const WillBeHeapVector<CSSPr
if (property.isImportant() != important)
continue;
const unsigned propertyIDIndex = property.id() - firstCSSProperty;
// All custom properties use the same CSSPropertyID so we can't remove repeated definitions
if (property.id() != CSSPropertyVariable) {
if (property.id() == CSSPropertyVariable) {
const AtomicString& name = toCSSCustomPropertyDeclaration(property.value())->name();
if (seenCustomProperties.contains(name))
continue;
seenCustomProperties.add(name);
} else {
if (seenProperties.get(propertyIDIndex))
continue;
seenProperties.set(propertyIDIndex);
......@@ -84,9 +89,10 @@ static PassRefPtrWillBeRawPtr<ImmutableStylePropertySet> createStylePropertySet(
BitArray<numCSSProperties> seenProperties;
size_t unusedEntries = parsedProperties.size();
WillBeHeapVector<CSSProperty, 256> results(unusedEntries);
HashSet<AtomicString> seenCustomProperties;
filterProperties(true, parsedProperties, results, unusedEntries, seenProperties);
filterProperties(false, parsedProperties, results, unusedEntries, seenProperties);
filterProperties(true, parsedProperties, results, unusedEntries, seenProperties, seenCustomProperties);
filterProperties(false, parsedProperties, results, unusedEntries, seenProperties, seenCustomProperties);
RefPtrWillBeRawPtr<ImmutableStylePropertySet> result = ImmutableStylePropertySet::create(results.data() + unusedEntries, results.size() - unusedEntries, mode);
parsedProperties.clear();
......@@ -119,8 +125,9 @@ bool CSSParserImpl::parseDeclarationList(MutableStylePropertySet* declaration, c
BitArray<numCSSProperties> seenProperties;
size_t unusedEntries = parser.m_parsedProperties.size();
WillBeHeapVector<CSSProperty, 256> results(unusedEntries);
filterProperties(true, parser.m_parsedProperties, results, unusedEntries, seenProperties);
filterProperties(false, parser.m_parsedProperties, results, unusedEntries, seenProperties);
HashSet<AtomicString> seenCustomProperties;
filterProperties(true, parser.m_parsedProperties, results, unusedEntries, seenProperties, seenCustomProperties);
filterProperties(false, parser.m_parsedProperties, results, unusedEntries, seenProperties, seenCustomProperties);
if (unusedEntries)
results.remove(0, unusedEntries);
return declaration->addParsedProperties(results);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment