Changeset 247537 in webkit
- Timestamp:
- Jul 17, 2019 2:18:30 PM (5 years ago)
- Location:
- trunk
- Files:
-
- 1 added
- 11 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/WTF/ChangeLog
r247523 r247537 1 2019-07-17 Sam Weinig <weinig@apple.com> 2 3 Add StringBuilder member function which allows makeString() style variadic argument construction 4 https://bugs.webkit.org/show_bug.cgi?id=198997 5 6 Reviewed by Darin Adler. 7 8 Adds new StringBuilder::flexibleAppend(...) member function which allows passing one or more 9 string-adaptable (in the sense that there is StringTypeAdapter specialization for the 10 type) parameters. This re-ususes the variadic template infrastructure in StringConcatenate.h 11 that is used for makeString(...) allowing for improvements in one to benefit the other. 12 13 The advantage of StringBuilder::flexibleAppend(...) over calling StringBuilder::append(...) 14 multiple times (beyond the code sharing with makeString(...) is that it can avoid unnecessary 15 additional re-allocations when the StringBuilder needs to expand it's capacity. It does this 16 by computing the complete required length for all the passed arguments and then ensuring enough 17 capacity is available. It also reduces the allocation overhead versus the anti-pattern of 18 builder.append(makeString(...)). 19 20 Ideally, this member function should eventually just be called StringBuilder::append(...), but 21 the current overload set for StringBuilder::append(...) makes this complicated due to overloads 22 that take two arguments such as StringBuilder::append(const UChar*, unsigned). Going forward, we 23 should rename or remove those overloads and move to a standard interface. 24 25 * wtf/posix/FileSystemPOSIX.cpp: 26 (WTF::FileSystemImpl::pathByAppendingComponents): 27 Adopt StringBuilder::flexibleAppend, using to combine the append of '/' and component. 28 29 * wtf/text/StringBuilder.cpp: 30 (WTF::StringBuilder::appendUninitialized): 31 (WTF::StringBuilder::appendUninitializedWithoutOverflowCheck): 32 Extract the part of appendUnitialized that doesn't do the overflow check 33 into it's own member function to allow callers that have already done the 34 overflow check to bypass it. 35 36 (WTF::StringBuilder::appendUninitializedWithoutOverflowCheckForUChar): 37 (WTF::StringBuilder::appendUninitializedWithoutOverflowCheckForLChar): 38 Added to allow template member function flexibleAppendFromAdapters to call 39 appendUninitializedWithoutOverflowCheck without moving it to the header. 40 41 * wtf/text/StringBuilder.h: 42 (WTF::StringBuilder::flexibleAppendFromAdapters): 43 (WTF::StringBuilder::flexibleAppend): 44 Modeled on tryMakeStringFromAdapters in StringConcatenate.h, these 45 eagerly compute the required length, expand the buffer and then use 46 the existing string type adaptor accumulation functions used by makeString. 47 48 * wtf/text/StringConcatenate.h: 49 (WTF::stringTypeAdapterAccumulator): 50 (WTF::tryMakeStringFromAdapters): 51 (WTF::makeStringAccumulator): Deleted. 52 Renames makeStringAccumulator to stringTypeAdapterAccumulator now that it is used 53 by more than just makeString. 54 1 55 2019-07-17 Commit Queue <commit-queue@webkit.org> 2 56 -
trunk/Source/WTF/wtf/posix/FileSystemPOSIX.cpp
r247307 r247537 302 302 StringBuilder builder; 303 303 builder.append(path); 304 for (auto& component : components) { 305 builder.append('/'); 306 builder.append(component); 307 } 304 for (auto& component : components) 305 builder.flexibleAppend('/', component); 308 306 return builder.toString(); 309 307 } -
trunk/Source/WTF/wtf/text/StringBuilder.cpp
r247307 r247537 164 164 } 165 165 166 template 166 template<> 167 167 void StringBuilder::reallocateBuffer<LChar>(unsigned requiredLength) 168 168 { … … 184 184 } 185 185 186 template 186 template<> 187 187 void StringBuilder::reallocateBuffer<UChar>(unsigned requiredLength) 188 188 { … … 232 232 } 233 233 234 // Make ' length' additional capacity be available in m_buffer, update m_string & m_length,234 // Make 'additionalLength' additional capacity be available in m_buffer, update m_string & m_length, 235 235 // return a pointer to the newly allocated storage. 236 236 // Returns nullptr if the size of the new builder would have overflowed 237 template <typename CharType>238 ALWAYS_INLINE Char Type* StringBuilder::appendUninitialized(unsigned length)239 { 240 ASSERT( length);237 template<typename CharacterType> 238 ALWAYS_INLINE CharacterType* StringBuilder::appendUninitialized(unsigned additionalLength) 239 { 240 ASSERT(additionalLength); 241 241 242 242 // Calculate the new size of the builder after appending. 243 CheckedInt32 requiredLength = m_length + length;243 CheckedInt32 requiredLength = m_length + additionalLength; 244 244 if (requiredLength.hasOverflowed()) { 245 245 didOverflow(); 246 246 return nullptr; 247 247 } 248 249 return appendUninitializedWithoutOverflowCheck<CharacterType>(requiredLength); 250 } 251 252 template<typename CharacterType> 253 ALWAYS_INLINE CharacterType* StringBuilder::appendUninitializedWithoutOverflowCheck(CheckedInt32 requiredLength) 254 { 255 ASSERT(!requiredLength.hasOverflowed()); 248 256 249 257 if (m_buffer && (requiredLength.unsafeGet<unsigned>() <= m_buffer->length())) { … … 253 261 m_string = String(); 254 262 m_length = requiredLength; 255 return getBufferCharacters<CharType>() + currentLength; 256 } 257 258 return appendUninitializedSlow<CharType>(requiredLength.unsafeGet()); 259 } 260 261 // Make 'length' additional capacity be available in m_buffer, update m_string & m_length, 263 return getBufferCharacters<CharacterType>() + currentLength; 264 } 265 266 return appendUninitializedSlow<CharacterType>(requiredLength.unsafeGet()); 267 } 268 269 UChar* StringBuilder::appendUninitializedWithoutOverflowCheckForUChar(CheckedInt32 requiredLength) 270 { 271 return appendUninitializedWithoutOverflowCheck<UChar>(requiredLength); 272 } 273 274 LChar* StringBuilder::appendUninitializedWithoutOverflowCheckForLChar(CheckedInt32 requiredLength) 275 { 276 return appendUninitializedWithoutOverflowCheck<LChar>(requiredLength); 277 } 278 279 // Make 'requiredLength' capacity be available in m_buffer, update m_string & m_length, 262 280 // return a pointer to the newly allocated storage. 263 template <typename CharType>264 Char Type* StringBuilder::appendUninitializedSlow(unsigned requiredLength)281 template<typename CharacterType> 282 CharacterType* StringBuilder::appendUninitializedSlow(unsigned requiredLength) 265 283 { 266 284 ASSERT(!hasOverflowed()); … … 271 289 ASSERT(m_buffer->length() >= m_length.unsafeGet<unsigned>()); 272 290 273 reallocateBuffer<Char Type>(expandedCapacity(capacity(), requiredLength));291 reallocateBuffer<CharacterType>(expandedCapacity(capacity(), requiredLength)); 274 292 } else { 275 293 ASSERT(m_string.length() == m_length.unsafeGet<unsigned>()); 276 allocateBuffer(m_length ? m_string.characters<Char Type>() : nullptr, expandedCapacity(capacity(), requiredLength));294 allocateBuffer(m_length ? m_string.characters<CharacterType>() : nullptr, expandedCapacity(capacity(), requiredLength)); 277 295 } 278 296 if (UNLIKELY(hasOverflowed())) 279 297 return nullptr; 280 298 281 Char Type* result = getBufferCharacters<CharType>() + m_length.unsafeGet();299 CharacterType* result = getBufferCharacters<CharacterType>() + m_length.unsafeGet(); 282 300 m_length = requiredLength; 283 301 ASSERT(!hasOverflowed()); -
trunk/Source/WTF/wtf/text/StringBuilder.h
r247307 r247537 232 232 WTF_EXPORT_PRIVATE void appendFixedWidthNumber(double, unsigned decimalPlaces); 233 233 234 // FIXME: Rename to append(...) after renaming any overloads of append that take more than one argument. 235 template<typename... StringTypes> void flexibleAppend(StringTypes...); 236 234 237 String toString() 235 238 { … … 351 354 void allocateBuffer(const UChar* currentCharacters, unsigned requiredLength); 352 355 void allocateBufferUpConvert(const LChar* currentCharacters, unsigned requiredLength); 353 template <typename CharType> 354 void reallocateBuffer(unsigned requiredLength); 355 template <typename CharType> 356 ALWAYS_INLINE CharType* appendUninitialized(unsigned length); 357 template <typename CharType> 358 CharType* appendUninitializedSlow(unsigned length); 359 template <typename CharType> 360 ALWAYS_INLINE CharType * getBufferCharacters(); 356 template<typename CharacterType> void reallocateBuffer(unsigned requiredLength); 357 template<typename CharacterType> ALWAYS_INLINE CharacterType* appendUninitialized(unsigned additionalLength); 358 template<typename CharacterType> ALWAYS_INLINE CharacterType* appendUninitializedWithoutOverflowCheck(CheckedInt32 requiredLength); 359 template<typename CharacterType> CharacterType* appendUninitializedSlow(unsigned requiredLength); 360 361 WTF_EXPORT_PRIVATE UChar* appendUninitializedWithoutOverflowCheckForUChar(CheckedInt32 requiredLength); 362 WTF_EXPORT_PRIVATE LChar* appendUninitializedWithoutOverflowCheckForLChar(CheckedInt32 requiredLength); 363 364 template<typename CharacterType> ALWAYS_INLINE CharacterType* getBufferCharacters(); 361 365 WTF_EXPORT_PRIVATE void reifyString() const; 366 367 template<typename... StringTypeAdapters> void flexibleAppendFromAdapters(StringTypeAdapters...); 362 368 363 369 mutable String m_string; … … 375 381 }; 376 382 377 template 383 template<> 378 384 ALWAYS_INLINE LChar* StringBuilder::getBufferCharacters<LChar>() 379 385 { … … 382 388 } 383 389 384 template 390 template<> 385 391 ALWAYS_INLINE UChar* StringBuilder::getBufferCharacters<UChar>() 386 392 { … … 389 395 } 390 396 391 template <typename CharType> 392 bool equal(const StringBuilder& s, const CharType* buffer, unsigned length) 397 template<typename... StringTypeAdapters> 398 void StringBuilder::flexibleAppendFromAdapters(StringTypeAdapters... adapters) 399 { 400 auto requiredLength = checkedSum<int32_t>(m_length, adapters.length()...); 401 if (requiredLength.hasOverflowed()) { 402 didOverflow(); 403 return; 404 } 405 406 if (m_is8Bit && are8Bit(adapters...)) { 407 LChar* dest = appendUninitializedWithoutOverflowCheckForLChar(requiredLength); 408 if (!dest) { 409 ASSERT(hasOverflowed()); 410 return; 411 } 412 stringTypeAdapterAccumulator(dest, adapters...); 413 } else { 414 UChar* dest = appendUninitializedWithoutOverflowCheckForUChar(requiredLength); 415 if (!dest) { 416 ASSERT(hasOverflowed()); 417 return; 418 } 419 stringTypeAdapterAccumulator(dest, adapters...); 420 } 421 } 422 423 template<typename... StringTypes> 424 void StringBuilder::flexibleAppend(StringTypes... strings) 425 { 426 flexibleAppendFromAdapters(StringTypeAdapter<StringTypes>(strings)...); 427 } 428 429 template<typename CharacterType> 430 bool equal(const StringBuilder& s, const CharacterType* buffer, unsigned length) 393 431 { 394 432 if (s.length() != length) … … 401 439 } 402 440 403 template 441 template<typename StringType> 404 442 bool equal(const StringBuilder& a, const StringType& b) 405 443 { -
trunk/Source/WTF/wtf/text/StringConcatenate.h
r247307 r247537 249 249 250 250 template<typename ResultType, typename Adapter> 251 inline void makeStringAccumulator(ResultType* result, Adapter adapter)251 inline void stringTypeAdapterAccumulator(ResultType* result, Adapter adapter) 252 252 { 253 253 adapter.writeTo(result); … … 255 255 256 256 template<typename ResultType, typename Adapter, typename... Adapters> 257 inline void makeStringAccumulator(ResultType* result, Adapter adapter, Adapters ...adapters)257 inline void stringTypeAdapterAccumulator(ResultType* result, Adapter adapter, Adapters ...adapters) 258 258 { 259 259 adapter.writeTo(result); 260 makeStringAccumulator(result + adapter.length(), adapters...);260 stringTypeAdapterAccumulator(result + adapter.length(), adapters...); 261 261 } 262 262 … … 277 277 return String(); 278 278 279 makeStringAccumulator(buffer, adapter, adapters...);279 stringTypeAdapterAccumulator(buffer, adapter, adapters...); 280 280 281 281 return resultImpl; … … 287 287 return String(); 288 288 289 makeStringAccumulator(buffer, adapter, adapters...);289 stringTypeAdapterAccumulator(buffer, adapter, adapters...); 290 290 291 291 return resultImpl; -
trunk/Tools/ChangeLog
r247536 r247537 1 2019-07-17 Sam Weinig <weinig@apple.com> 2 3 Add StringBuilder member function which allows makeString() style variadic argument construction 4 https://bugs.webkit.org/show_bug.cgi?id=198997 5 6 Reviewed by Darin Adler. 7 8 * TestWebKitAPI/Tests/WTF/StringBuilder.cpp: 9 Add basic test showing that StringBuilder::flexibleAppend can be used to 10 append one or more string adaptable types. 11 12 * TestWebKitAPI/CMakeLists.txt: 13 * TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj: 14 Add WTFStringUtilities.cpp 15 16 * TestWebKitAPI/Tests/WTF/StringBuilder.cpp: 17 Add basic test showing that StringBuilder::flexibleAppend can be used to 18 append one or more string adaptable types. 19 20 * TestWebKitAPI/Tests/WTF/StringOperators.cpp: 21 * TestWebKitAPI/WTFStringUtilities.cpp: Added. 22 * TestWebKitAPI/WTFStringUtilities.h: 23 Move WTF_STRINGTYPEADAPTER_COPIED_WTF_STRING() and wtfStringCopyCount to WTFStringUtilities.h/cpp 24 to allow for a single definition of StringTypeAdapter<String, void> which is required for ODR. 25 1 26 2019-07-17 Ryosuke Niwa <rniwa@webkit.org> 2 27 -
trunk/Tools/TestWebKitAPI/CMakeLists.txt
r246623 r247537 24 24 Counters.cpp 25 25 TestsController.cpp 26 WTFStringUtilities.cpp 26 27 27 28 Tests/WTF/AtomString.cpp … … 117 118 set(TestWebCore_SOURCES 118 119 TestsController.cpp 120 WTFStringUtilities.cpp 119 121 120 122 Tests/WebCore/AffineTransform.cpp … … 166 168 set(TestWebKitLegacy_SOURCES 167 169 TestsController.cpp 170 WTFStringUtilities.cpp 168 171 ) 169 172 … … 267 270 PlatformUtilities.cpp 268 271 TestsController.cpp 272 WTFStringUtilities.cpp 269 273 ) 270 274 target_compile_definitions(TestWebKitAPIBase PRIVATE BUILDING_TestWebKit) -
trunk/Tools/TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj
r247524 r247537 428 428 7C417F331D19E14800B8EF53 /* WKWebViewDefaultNavigationDelegate.mm in Sources */ = {isa = PBXBuildFile; fileRef = 7C417F311D19E14800B8EF53 /* WKWebViewDefaultNavigationDelegate.mm */; }; 429 429 7C486BA11AA12567003F6F9B /* bundle-file.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = 7C486BA01AA1254B003F6F9B /* bundle-file.html */; }; 430 7C74C8FA22DFBA9600DA2DAB /* WTFStringUtilities.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CBD5A2222DE42A6004A9E32 /* WTFStringUtilities.cpp */; }; 430 431 7C83DE991D0A590C00FEBCF3 /* AtomString.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26F1B44215CA434F00D1E4BF /* AtomString.cpp */; }; 431 432 7C83DE9C1D0A590C00FEBCF3 /* BloomFilter.cpp in Sources */ = {isa = PBXBuildFile; fileRef = E40019301ACE9B5C001B0A2A /* BloomFilter.cpp */; }; … … 509 510 7C9ED98B17A19F4B00E4DC33 /* attributedStringStrikethrough.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = 7C9ED98A17A19D0600E4DC33 /* attributedStringStrikethrough.html */; }; 510 511 7CB184C61AA3F2100066EDFD /* ContentExtensions.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CB184C41AA3F2100066EDFD /* ContentExtensions.cpp */; }; 512 7CBD5A2322DE42A6004A9E32 /* WTFStringUtilities.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CBD5A2222DE42A6004A9E32 /* WTFStringUtilities.cpp */; }; 511 513 7CCB4DA91C83AE7300CC6918 /* PageGroup.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CCB4DA71C83AE7300CC6918 /* PageGroup.cpp */; }; 512 514 7CCB99211D3B41F6003922F6 /* UserInitiatedActionInNavigationAction.mm in Sources */ = {isa = PBXBuildFile; fileRef = 7CCB99201D3B41F6003922F6 /* UserInitiatedActionInNavigationAction.mm */; }; … … 1927 1929 7CB184C41AA3F2100066EDFD /* ContentExtensions.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ContentExtensions.cpp; sourceTree = "<group>"; }; 1928 1930 7CBBA07619BB8A9100BBF025 /* OSObjectPtr.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = OSObjectPtr.cpp; sourceTree = "<group>"; }; 1931 7CBD5A2222DE42A6004A9E32 /* WTFStringUtilities.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = WTFStringUtilities.cpp; sourceTree = "<group>"; }; 1929 1932 7CC3E1FA197E234100BE6252 /* UserContentController.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = UserContentController.mm; sourceTree = "<group>"; }; 1930 1933 7CCB4DA71C83AE7300CC6918 /* PageGroup.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PageGroup.cpp; sourceTree = "<group>"; }; … … 2563 2566 7C83E0361D0A5F7000FEBCF3 /* Utilities.h */, 2564 2567 44A622C114A0E2B60048515B /* WTFStringUtilities.h */, 2568 7CBD5A2222DE42A6004A9E32 /* WTFStringUtilities.cpp */, 2565 2569 ); 2566 2570 name = Source; … … 4131 4135 7C83DE991D0A590C00FEBCF3 /* AtomString.cpp in Sources */, 4132 4136 1ADAD1501D77A9F600212586 /* BlockPtr.mm in Sources */, 4137 7CBD5A2322DE42A6004A9E32 /* WTFStringUtilities.cpp in Sources */, 4133 4138 7C83DE9C1D0A590C00FEBCF3 /* BloomFilter.cpp in Sources */, 4134 4139 7C83DEA01D0A590C00FEBCF3 /* CheckedArithmeticOperations.cpp in Sources */, … … 4286 4291 5C2936931D5BF70D00DEAB1E /* CookieAcceptPolicy.mm in Sources */, 4287 4292 51D1249B1E785425002B2820 /* CookieManager.cpp in Sources */, 4293 7C74C8FA22DFBA9600DA2DAB /* WTFStringUtilities.cpp in Sources */, 4288 4294 5C19A5241FD0F60100EEA323 /* CookiePrivateBrowsing.mm in Sources */, 4289 4295 9B1F6F781F90558400B55744 /* CopyHTML.mm in Sources */, -
trunk/Tools/TestWebKitAPI/Tests/WTF/StringBuilder.cpp
r247307 r247537 117 117 } 118 118 119 TEST(StringBuilderTest, FlexibleAppend) 120 { 121 { 122 StringBuilder builder; 123 builder.flexibleAppend(String("0123456789")); 124 expectBuilderContent("0123456789", builder); 125 builder.flexibleAppend("abcd"); 126 expectBuilderContent("0123456789abcd", builder); 127 builder.flexibleAppend('e'); 128 expectBuilderContent("0123456789abcde", builder); 129 builder.flexibleAppend(""); 130 expectBuilderContent("0123456789abcde", builder); 131 } 132 133 { 134 StringBuilder builder; 135 builder.flexibleAppend(String("0123456789"), "abcd", 'e', ""); 136 expectBuilderContent("0123456789abcde", builder); 137 builder.flexibleAppend(String("A"), "B", 'C', ""); 138 expectBuilderContent("0123456789abcdeABC", builder); 139 } 140 } 141 119 142 TEST(StringBuilderTest, ToString) 120 143 { -
trunk/Tools/TestWebKitAPI/Tests/WTF/StringOperators.cpp
r246490 r247537 26 26 #include "config.h" 27 27 28 #define WTF_STRINGTYPEADAPTER_COPIED_WTF_STRING() (++wtfStringCopyCount) 29 30 static int wtfStringCopyCount; 28 #include "WTFStringUtilities.h" 31 29 32 30 #include <wtf/text/StringView.h> -
trunk/Tools/TestWebKitAPI/WTFStringUtilities.h
r209857 r247537 31 31 #pragma once 32 32 33 #define WTF_STRINGTYPEADAPTER_COPIED_WTF_STRING() (++wtfStringCopyCount) 34 35 extern int wtfStringCopyCount; 36 33 37 #include <wtf/Assertions.h> 34 38 #include <wtf/text/CString.h>
Note: See TracChangeset
for help on using the changeset viewer.