OLD | NEW |
1 /* | 1 /* |
2 * (C) 1999-2003 Lars Knoll (knoll@kde.org) | 2 * (C) 1999-2003 Lars Knoll (knoll@kde.org) |
3 * Copyright (C) 2004, 2005, 2006, 2007, 2008 Apple Inc. All rights reserved. | 3 * Copyright (C) 2004, 2005, 2006, 2007, 2008 Apple Inc. All rights reserved. |
4 * | 4 * |
5 * This library is free software; you can redistribute it and/or | 5 * This library is free software; you can redistribute it and/or |
6 * modify it under the terms of the GNU Library General Public | 6 * modify it under the terms of the GNU Library General Public |
7 * License as published by the Free Software Foundation; either | 7 * License as published by the Free Software Foundation; either |
8 * version 2 of the License, or (at your option) any later version. | 8 * version 2 of the License, or (at your option) any later version. |
9 * | 9 * |
10 * This library is distributed in the hope that it will be useful, | 10 * This library is distributed in the hope that it will be useful, |
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of | 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of |
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
13 * Library General Public License for more details. | 13 * Library General Public License for more details. |
14 * | 14 * |
15 * You should have received a copy of the GNU Library General Public License | 15 * You should have received a copy of the GNU Library General Public License |
16 * along with this library; see the file COPYING.LIB. If not, write to | 16 * along with this library; see the file COPYING.LIB. If not, write to |
17 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, | 17 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, |
18 * Boston, MA 02110-1301, USA. | 18 * Boston, MA 02110-1301, USA. |
19 */ | 19 */ |
20 | 20 |
21 #ifndef CSSValue_h | 21 #ifndef CSSValue_h |
22 #define CSSValue_h | 22 #define CSSValue_h |
23 | 23 |
24 #include "core/CoreExport.h" | 24 #include "core/CoreExport.h" |
| 25 #include "core/css/CSSValueObject.h" |
25 #include "platform/heap/Handle.h" | 26 #include "platform/heap/Handle.h" |
26 #include "platform/weborigin/KURL.h" | |
27 #include "wtf/HashMap.h" | |
28 #include "wtf/ListHashSet.h" | |
29 #include "wtf/RefCounted.h" | 27 #include "wtf/RefCounted.h" |
30 #include "wtf/RefPtr.h" | 28 #include "wtf/RefPtr.h" |
31 | 29 |
32 namespace blink { | 30 namespace blink { |
33 | 31 |
34 class CORE_EXPORT CSSValue : public RefCountedWillBeGarbageCollectedFinalized<CS
SValue> { | 32 // A non-nullable container for CSSValueObject. Takes ownership of the passed |
| 33 // CSSValueObject. |
| 34 class CORE_EXPORT CSSValue { |
| 35 ALLOW_ONLY_INLINE_ALLOCATION(); |
| 36 friend class NullableCSSValue; |
35 public: | 37 public: |
36 #if ENABLE(OILPAN) | 38 // Not explicit to allow for casting. |
37 // Override operator new to allocate CSSValue subtype objects onto | 39 CSSValue(const CSSValueObject& cssValueObject) |
38 // a dedicated heap. | 40 : m_data(const_cast<CSSValueObject*>(&cssValueObject)) |
39 GC_PLUGIN_IGNORE("crbug.com/443854") | 41 { |
40 void* operator new(size_t size) | 42 ASSERT(m_data); |
41 { | 43 ref(); |
42 return allocateObject(size, false); | 44 } |
43 } | 45 |
44 static void* allocateObject(size_t size, bool isEager) | 46 // TODO(sashab): Remove these; construction should only be available with |
45 { | 47 // CSSValueObject&. |
46 ThreadState* state = ThreadStateFor<ThreadingTrait<CSSValue>::Affinity>:
:state(); | 48 template<class T> CSSValue(PassRefPtrWillBeRawPtr<T> cssValueObject) |
47 return Heap::allocateOnHeapIndex(state, size, isEager ? ThreadState::Eag
erSweepHeapIndex : ThreadState::CSSValueHeapIndex, GCInfoTrait<CSSValue>::index(
)); | 49 : m_data(cssValueObject.leakRef()) |
48 } | 50 { |
49 #else | 51 static_assert(WTF::IsSubclass<T, CSSValueObject>::value, "Parameter must
be a container for CSSValueObject"); |
50 // Override RefCounted's deref() to ensure operator delete is called on | 52 ASSERT(m_data); |
51 // the appropriate subclass type. | 53 } |
52 void deref() | 54 |
53 { | 55 #if !ENABLE(OILPAN) |
54 if (derefBase()) | 56 template<class T> CSSValue(RefPtrWillBeRawPtr<T> cssValueObject) |
55 destroy(); | 57 : m_data(cssValueObject.release().leakRef()) |
56 } | 58 { |
57 #endif // !ENABLE(OILPAN) | 59 static_assert(WTF::IsSubclass<T, CSSValueObject>::value, "Parameter must
be a container for CSSValueObject"); |
58 | 60 ASSERT(m_data); |
59 String cssText() const; | 61 } |
60 | 62 #endif |
61 bool isPrimitiveValue() const { return m_classType == PrimitiveClass; } | 63 |
62 bool isValueList() const { return m_classType >= ValueListClass; } | 64 CSSValue(const CSSValue& cssValue) |
63 | 65 : m_data(cssValue.m_data) |
64 bool isBaseValueList() const { return m_classType == ValueListClass; } | 66 { |
65 | 67 ref(); |
66 bool isBorderImageSliceValue() const { return m_classType == BorderImageSlic
eClass; } | 68 } |
67 bool isCanvasValue() const { return m_classType == CanvasClass; } | 69 |
68 bool isCursorImageValue() const { return m_classType == CursorImageClass; } | 70 ~CSSValue() |
69 bool isCrossfadeValue() const { return m_classType == CrossfadeClass; } | 71 { |
70 bool isFontFeatureValue() const { return m_classType == FontFeatureClass; } | 72 deref(); |
71 bool isFontFaceSrcValue() const { return m_classType == FontFaceSrcClass; } | 73 } |
72 bool isFunctionValue() const { return m_classType == FunctionClass; } | 74 |
73 bool isImageGeneratorValue() const { return m_classType >= CanvasClass && m_
classType <= RadialGradientClass; } | 75 CSSValue& operator=(const CSSValue& rhs) |
74 bool isGradientValue() const { return m_classType >= LinearGradientClass &&
m_classType <= RadialGradientClass; } | 76 { |
75 bool isImageSetValue() const { return m_classType == ImageSetClass; } | 77 rhs.ref(); |
76 bool isImageValue() const { return m_classType == ImageClass; } | 78 deref(); |
77 bool isImplicitInitialValue() const; | 79 m_data = rhs.m_data; |
78 bool isInheritedValue() const { return m_classType == InheritedClass; } | 80 return *this; |
79 bool isInitialValue() const { return m_classType == InitialClass; } | 81 } |
80 bool isUnsetValue() const { return m_classType == UnsetClass; } | 82 |
81 bool isCSSWideKeyword() const { return m_classType >= InheritedClass && m_cl
assType <= UnsetClass; } | 83 bool operator==(const CSSValue& other) const |
82 bool isLinearGradientValue() const { return m_classType == LinearGradientCla
ss; } | 84 { |
83 bool isPathValue() const { return m_classType == PathClass; } | 85 return m_data->equals(*other.m_data); |
84 bool isRadialGradientValue() const { return m_classType == RadialGradientCla
ss; } | 86 } |
85 bool isReflectValue() const { return m_classType == ReflectClass; } | 87 |
86 bool isShadowValue() const { return m_classType == ShadowClass; } | 88 // TODO: Remove this and update callsites to use operator== instead. |
87 bool isCubicBezierTimingFunctionValue() const { return m_classType == CubicB
ezierTimingFunctionClass; } | 89 bool equals(const CSSValue& other) const |
88 bool isStepsTimingFunctionValue() const { return m_classType == StepsTimingF
unctionClass; } | 90 { |
89 bool isLineBoxContainValue() const { return m_classType == LineBoxContainCla
ss; } | 91 return m_data->equals(*other.m_data); |
90 bool isCalcValue() const {return m_classType == CalculationClass; } | 92 } |
91 bool isGridTemplateAreasValue() const { return m_classType == GridTemplateAr
easClass; } | 93 |
92 bool isSVGDocumentValue() const { return m_classType == CSSSVGDocumentClass;
} | 94 bool ptrEquals(const CSSValue& other) const |
93 bool isContentDistributionValue() const { return m_classType == CSSContentDi
stributionClass; } | 95 { |
94 bool isUnicodeRangeValue() const { return m_classType == UnicodeRangeClass;
} | 96 return m_data == other.m_data; |
95 bool isGridLineNamesValue() const { return m_classType == GridLineNamesClass
; } | 97 } |
96 | 98 |
97 bool hasFailedOrCanceledSubresources() const; | 99 // Methods that proxy to CSSValueObject. |
98 | 100 String cssText() const { return m_data->cssText(); } |
99 bool equals(const CSSValue&) const; | 101 bool hasFailedOrCanceledSubresources() const { return m_data->hasFailedOrCan
celedSubresources(); }; |
100 | 102 bool isPrimitiveValue() const { return m_data->isPrimitiveValue(); } |
101 void finalizeGarbageCollectedObject(); | 103 bool isValueList() const { return m_data->isValueList(); } |
102 DEFINE_INLINE_TRACE_AFTER_DISPATCH() { } | 104 bool isBaseValueList() const { return m_data->isBaseValueList(); } |
103 DECLARE_TRACE(); | 105 bool isBorderImageSliceValue() const { return m_data->isBorderImageSliceValu
e(); } |
104 | 106 bool isCanvasValue() const { return m_data->isCanvasValue(); } |
105 // ~CSSValue should be public, because non-public ~CSSValue causes C2248 | 107 bool isCursorImageValue() const { return m_data->isCursorImageValue(); } |
106 // error: 'blink::CSSValue::~CSSValue' : cannot access protected member | 108 bool isCrossfadeValue() const { return m_data->isCrossfadeValue(); } |
107 // declared in class 'blink::CSSValue' when compiling | 109 bool isFontFeatureValue() const { return m_data->isFontFeatureValue(); } |
108 // 'source\wtf\refcounted.h' by using msvc. | 110 bool isFontFaceSrcValue() const { return m_data->isFontFaceSrcValue(); } |
109 ~CSSValue() { } | 111 bool isFunctionValue() const { return m_data->isFunctionValue(); } |
110 | 112 bool isImageGeneratorValue() const { return m_data->isImageGeneratorValue();
} |
111 protected: | 113 bool isGradientValue() const { return m_data->isGradientValue(); } |
112 | 114 bool isImageSetValue() const { return m_data->isImageSetValue(); } |
113 static const size_t ClassTypeBits = 6; | 115 bool isImageValue() const { return m_data->isImageValue(); } |
114 enum ClassType { | 116 bool isImplicitInitialValue() const { return m_data->isImplicitInitialValue(
); }; |
115 PrimitiveClass, | 117 bool isInheritedValue() const { return m_data->isInheritedValue(); }; |
116 | 118 bool isInitialValue() const { return m_data->isInitialValue(); }; |
117 // Image classes. | 119 bool isUnsetValue() const { return m_data->isUnsetValue(); }; |
118 ImageClass, | 120 bool isCSSWideKeyword() const { return m_data->isCSSWideKeyword(); }; |
119 CursorImageClass, | 121 bool isLinearGradientValue() const { return m_data->isLinearGradientValue();
}; |
120 | 122 bool isPathValue() const { return m_data->isPathValue(); }; |
121 // Image generator classes. | 123 bool isRadialGradientValue() const { return m_data->isRadialGradientValue();
}; |
122 CanvasClass, | 124 bool isReflectValue() const { return m_data->isReflectValue(); }; |
123 CrossfadeClass, | 125 bool isShadowValue() const { return m_data->isShadowValue(); }; |
124 LinearGradientClass, | 126 bool isCubicBezierTimingFunctionValue() const { return m_data->isCubicBezier
TimingFunctionValue(); }; |
125 RadialGradientClass, | 127 bool isStepsTimingFunctionValue() const { return m_data->isStepsTimingFuncti
onValue(); }; |
126 | 128 bool isLineBoxContainValue() const { return m_data->isLineBoxContainValue();
}; |
127 // Timing function classes. | 129 bool isCalcValue() const { return m_data->isCalcValue(); }; |
128 CubicBezierTimingFunctionClass, | 130 bool isGridTemplateAreasValue() const { return m_data->isGridTemplateAreasVa
lue(); }; |
129 StepsTimingFunctionClass, | 131 bool isSVGDocumentValue() const { return m_data->isSVGDocumentValue(); }; |
130 | 132 bool isContentDistributionValue() const { return m_data->isContentDistributi
onValue(); }; |
131 // Other class types. | 133 bool isUnicodeRangeValue() const { return m_data->isUnicodeRangeValue(); }; |
132 BorderImageSliceClass, | 134 bool isGridLineNamesValue() const { return m_data->isGridLineNamesValue(); }
; |
133 FontFeatureClass, | 135 |
134 FontFaceSrcClass, | 136 DEFINE_INLINE_TRACE() |
135 | 137 { |
136 InheritedClass, | 138 ASSERT(m_data); |
137 InitialClass, | 139 visitor->trace(m_data); |
138 UnsetClass, | 140 } |
139 | 141 |
140 ReflectClass, | 142 // Only for use by the toFooCSSValue() macros. Don't use this. |
141 ShadowClass, | 143 // TODO(sashab): Remove this and use value.to<Type> and value.isValid<Type> |
142 UnicodeRangeClass, | 144 // like WebNode. |
143 LineBoxContainClass, | 145 CSSValueObject* get() const |
144 CalculationClass, | 146 { |
145 GridTemplateAreasClass, | 147 return m_data.get(); |
146 PathClass, | 148 } |
147 | 149 |
148 // SVG classes. | 150 private: |
149 CSSSVGDocumentClass, | 151 CSSValue() = delete; // compile-time guard |
150 | 152 CSSValue(std::nullptr_t) = delete; // compile-time guard |
151 CSSContentDistributionClass, | 153 |
152 | 154 void ref() const |
153 // List class types must appear after ValueListClass. | 155 { |
154 ValueListClass, | 156 #if !ENABLE(OILPAN) |
155 FunctionClass, | 157 if (m_data) |
156 ImageSetClass, | 158 m_data->ref(); |
157 GridLineNamesClass, | 159 #endif |
158 // Do not append non-list class types here. | 160 } |
| 161 |
| 162 void deref() const |
| 163 { |
| 164 #if !ENABLE(OILPAN) |
| 165 if (m_data) |
| 166 m_data->deref(); |
| 167 #endif |
| 168 } |
| 169 |
| 170 RawPtrWillBeMember<CSSValueObject> m_data; |
| 171 }; |
| 172 |
| 173 // A nullable container for CSSValueObject. Contents are the same as CSSValue. |
| 174 // Behavior is similar to a CSSValue*. |
| 175 class CORE_EXPORT NullableCSSValue { |
| 176 ALLOW_ONLY_INLINE_ALLOCATION(); |
| 177 public: |
| 178 // Not explicit to allow for casting. |
| 179 NullableCSSValue() |
| 180 : m_data(nullptr) |
| 181 { |
| 182 } |
| 183 |
| 184 NullableCSSValue(const CSSValueObject* cssValueObject) |
| 185 : m_data(const_cast<CSSValueObject*>(cssValueObject)) |
| 186 { |
| 187 ref(); |
| 188 } |
| 189 |
| 190 NullableCSSValue(const CSSValueObject& cssValueObject) |
| 191 : m_data(const_cast<CSSValueObject*>(&cssValueObject)) |
| 192 { |
| 193 ref(); |
| 194 } |
| 195 |
| 196 // TODO(sashab): Remove these; construction should only be available with |
| 197 // CSSValueObject& or CSSValueObject*. |
| 198 template <class T> NullableCSSValue(PassRefPtrWillBeRawPtr<T> cssValueObject
) |
| 199 : m_data(cssValueObject.leakRef()) |
| 200 { |
| 201 static_assert(WTF::IsSubclass<T, CSSValueObject>::value, "Parameter must
be a container for CSSValueObject"); |
| 202 } |
| 203 |
| 204 #if !ENABLE(OILPAN) |
| 205 template <class T> NullableCSSValue(RefPtrWillBeRawPtr<T> cssValueObject) |
| 206 : m_data(cssValueObject.release().leakRef()) |
| 207 { |
| 208 static_assert(WTF::IsSubclass<T, CSSValueObject>::value, "Parameter must
be a container for CSSValueObject"); |
| 209 } |
| 210 #endif |
| 211 |
| 212 NullableCSSValue(const NullableCSSValue& cssValue) |
| 213 : m_data(cssValue.m_data) |
| 214 { |
| 215 ref(); |
| 216 } |
| 217 |
| 218 NullableCSSValue(const CSSValue& cssValue) |
| 219 : m_data(cssValue.m_data) |
| 220 { |
| 221 ref(); |
| 222 } |
| 223 |
| 224 ~NullableCSSValue() |
| 225 { |
| 226 deref(); |
159 }; | 227 }; |
160 | 228 |
161 static const size_t ValueListSeparatorBits = 2; | 229 operator bool() const |
162 enum ValueListSeparator { | 230 { |
163 SpaceSeparator, | 231 return m_data; |
164 CommaSeparator, | 232 } |
165 SlashSeparator | 233 |
166 }; | 234 NullableCSSValue& operator=(const NullableCSSValue& rhs) |
167 | 235 { |
168 ClassType classType() const { return static_cast<ClassType>(m_classType); } | 236 rhs.ref(); |
169 | 237 deref(); |
170 explicit CSSValue(ClassType classType) | 238 m_data = rhs.m_data; |
171 : m_primitiveUnitType(0) | 239 return *this; |
172 , m_hasCachedCSSText(false) | 240 } |
173 , m_isQuirkValue(false) | 241 |
174 , m_valueListSeparator(SpaceSeparator) | 242 bool operator==(const NullableCSSValue& rhs) |
175 , m_classType(classType) | 243 { |
176 { | 244 return m_data ? rhs.m_data && m_data->equals(*rhs.m_data) : !bool(rhs.m_
data); |
177 } | 245 } |
178 | 246 |
179 // NOTE: This class is non-virtual for memory and performance reasons. | 247 bool operator!=(const NullableCSSValue& rhs) |
180 // Don't go making it virtual again unless you know exactly what you're doin
g! | 248 { |
| 249 return !(*this == rhs); |
| 250 } |
| 251 |
| 252 CSSValue& operator*() |
| 253 { |
| 254 ASSERT(m_data); |
| 255 // reinterpret_casts used to avoid ref-churn. |
| 256 return *reinterpret_cast<CSSValue*>(this); |
| 257 } |
| 258 |
| 259 const CSSValue& operator*() const |
| 260 { |
| 261 ASSERT(m_data); |
| 262 return *reinterpret_cast<const CSSValue*>(this); |
| 263 } |
| 264 |
| 265 CSSValue* operator->() |
| 266 { |
| 267 ASSERT(m_data); |
| 268 return reinterpret_cast<CSSValue*>(this); |
| 269 } |
| 270 |
| 271 const CSSValue* operator->() const |
| 272 { |
| 273 ASSERT(m_data); |
| 274 return reinterpret_cast<const CSSValue*>(this); |
| 275 } |
| 276 |
| 277 void swap(NullableCSSValue& rhs) |
| 278 { |
| 279 std::swap(this->m_data, rhs.m_data); |
| 280 } |
| 281 |
| 282 DEFINE_INLINE_TRACE() |
| 283 { |
| 284 visitor->trace(m_data); |
| 285 } |
| 286 |
| 287 // Only for use by the toFooCSSValue() macros. Don't use this. |
| 288 // TODO(sashab): Remove this and use value.to<Type> and value.isValid<Type> |
| 289 // like WebNode. |
| 290 CSSValueObject* get() const |
| 291 { |
| 292 return m_data.get(); |
| 293 } |
181 | 294 |
182 private: | 295 private: |
183 void destroy(); | 296 void ref() const |
184 | 297 { |
185 protected: | 298 #if !ENABLE(OILPAN) |
186 // The bits in this section are only used by specific subclasses but kept he
re | 299 if (m_data) |
187 // to maximize struct packing. | 300 m_data->ref(); |
188 | 301 #endif |
189 // CSSPrimitiveValue bits: | 302 } |
190 unsigned m_primitiveUnitType : 7; // CSSPrimitiveValue::UnitType | 303 |
191 mutable unsigned m_hasCachedCSSText : 1; | 304 void deref() const |
192 unsigned m_isQuirkValue : 1; | 305 { |
193 | 306 #if !ENABLE(OILPAN) |
194 unsigned m_valueListSeparator : ValueListSeparatorBits; | 307 if (m_data) |
195 | 308 m_data->deref(); |
196 private: | 309 #endif |
197 unsigned m_classType : ClassTypeBits; // ClassType | 310 } |
| 311 |
| 312 RawPtrWillBeMember<CSSValueObject> m_data; |
198 }; | 313 }; |
199 | 314 |
200 template<typename CSSValueType, size_t inlineCapacity> | 315 static_assert(sizeof(CSSValue) == sizeof(void*), "CSSValue should be pointer-siz
ed"); |
201 inline bool compareCSSValueVector(const WillBeHeapVector<RefPtrWillBeMember<CSSV
alueType>, inlineCapacity>& firstVector, const WillBeHeapVector<RefPtrWillBeMemb
er<CSSValueType>, inlineCapacity>& secondVector) | 316 static_assert(sizeof(NullableCSSValue) == sizeof(void*), "CSSValue should be poi
nter-sized"); |
| 317 static_assert(sizeof(CSSValue) == sizeof(NullableCSSValue), "Both CSSValue conta
iners must contain the same data"); |
| 318 |
| 319 template<size_t inlineCapacity> |
| 320 inline bool compareCSSValueVector(const WillBeHeapVector<CSSValue, inlineCapacit
y>& firstVector, const WillBeHeapVector<CSSValue, inlineCapacity>& secondVector) |
202 { | 321 { |
203 size_t size = firstVector.size(); | 322 size_t size = firstVector.size(); |
204 if (size != secondVector.size()) | 323 if (size != secondVector.size()) |
205 return false; | 324 return false; |
206 | 325 |
207 for (size_t i = 0; i < size; i++) { | 326 for (size_t i = 0; i < size; i++) { |
208 const RefPtrWillBeMember<CSSValueType>& firstPtr = firstVector[i]; | 327 const CSSValue& firstPtr = firstVector[i]; |
209 const RefPtrWillBeMember<CSSValueType>& secondPtr = secondVector[i]; | 328 const CSSValue& secondPtr = secondVector[i]; |
210 if (firstPtr == secondPtr || (firstPtr && secondPtr && firstPtr->equals(
*secondPtr))) | 329 if (firstPtr.ptrEquals(secondPtr) || firstPtr.equals(secondPtr)) |
211 continue; | 330 continue; |
212 return false; | 331 return false; |
213 } | 332 } |
214 return true; | 333 return true; |
215 } | 334 } |
216 | 335 |
217 template<typename CSSValueType> | |
218 inline bool compareCSSValuePtr(const RefPtr<CSSValueType>& first, const RefPtr<C
SSValueType>& second) | |
219 { | |
220 if (first == second) | |
221 return true; | |
222 if (!first || !second) | |
223 return false; | |
224 return first->equals(*second); | |
225 } | |
226 | |
227 template<typename CSSValueType> | |
228 inline bool compareCSSValuePtr(const RawPtr<CSSValueType>& first, const RawPtr<C
SSValueType>& second) | |
229 { | |
230 if (first == second) | |
231 return true; | |
232 if (!first || !second) | |
233 return false; | |
234 return first->equals(*second); | |
235 } | |
236 | |
237 template<typename CSSValueType> | |
238 inline bool compareCSSValuePtr(const Member<CSSValueType>& first, const Member<C
SSValueType>& second) | |
239 { | |
240 if (first == second) | |
241 return true; | |
242 if (!first || !second) | |
243 return false; | |
244 return first->equals(*second); | |
245 } | |
246 | |
247 #define DEFINE_CSS_VALUE_TYPE_CASTS(thisType, predicate) \ | 336 #define DEFINE_CSS_VALUE_TYPE_CASTS(thisType, predicate) \ |
248 DEFINE_TYPE_CASTS(thisType, CSSValue, value, value->predicate, value.predica
te) | 337 DEFINE_TYPE_CASTS(thisType, CSSValueObject, value, value->predicate, value.p
redicate); \ |
| 338 inline thisType& to##thisType(const CSSValue& value) \ |
| 339 { \ |
| 340 ASSERT_WITH_SECURITY_IMPLICATION(value.predicate); \ |
| 341 return *static_cast<thisType*>(value.get()); \ |
| 342 } \ |
| 343 inline thisType* to##thisType(const NullableCSSValue& value) \ |
| 344 { \ |
| 345 if (!value) \ |
| 346 return nullptr; \ |
| 347 ASSERT_WITH_SECURITY_IMPLICATION(value->predicate); \ |
| 348 return static_cast<thisType*>(value.get()); \ |
| 349 } |
249 | 350 |
250 } // namespace blink | 351 } // namespace blink |
251 | 352 |
| 353 WTF_ALLOW_CLEAR_UNUSED_SLOTS_WITH_MEM_FUNCTIONS(blink::CSSValue); |
| 354 WTF_ALLOW_CLEAR_UNUSED_SLOTS_WITH_MEM_FUNCTIONS(blink::NullableCSSValue); |
| 355 |
252 #endif // CSSValue_h | 356 #endif // CSSValue_h |
OLD | NEW |