Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(89)

Unified Diff: third_party/WebKit/Source/wtf/text/StringBuilder.cpp

Issue 2106283004: Allocate space in StringBuilder for m_string and the new bytes. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 4 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: third_party/WebKit/Source/wtf/text/StringBuilder.cpp
diff --git a/third_party/WebKit/Source/wtf/text/StringBuilder.cpp b/third_party/WebKit/Source/wtf/text/StringBuilder.cpp
index e1922ae1bc21f92362cc71e10faff7116bf4a6ff..10d09e5d7ecba08c91a4de15caf5ed4fcb8610ea 100644
--- a/third_party/WebKit/Source/wtf/text/StringBuilder.cpp
+++ b/third_party/WebKit/Source/wtf/text/StringBuilder.cpp
@@ -102,13 +102,10 @@ unsigned StringBuilder::capacity() const
void StringBuilder::reserveCapacity(unsigned newCapacity)
{
- if (m_is8Bit) {
- ensureBuffer8();
- m_buffer8->reserveCapacity(newCapacity);
- } else {
- ensureBuffer16();
- m_buffer16->reserveCapacity(newCapacity);
- }
+ if (m_is8Bit)
+ ensureBuffer8(newCapacity);
+ else
+ ensureBuffer16(newCapacity);
}
void StringBuilder::resize(unsigned newSize)
@@ -124,18 +121,28 @@ void StringBuilder::resize(unsigned newSize)
m_buffer16->resize(newSize);
}
-void StringBuilder::createBuffer8()
+void StringBuilder::createBuffer8(unsigned addedSize)
{
DCHECK(!hasBuffer());
DCHECK(m_is8Bit);
m_buffer8 = new Buffer8;
+ // createBuffer is called right before appending addedSize more bytes. We
+ // want to ensure we have enough space to fit m_string plus the added
+ // size.
+ //
+ // We also ensure that we have at least the initialBufferSize of extra space
+ // for appending new bytes to avoid future mallocs for appending short
+ // strings or single characters. This is a no-op if m_length == 0 since
+ // initialBufferSize() is the same as the inline capacity of the vector.
+ // This allows doing append(string); append('\0') without extra mallocs.
+ m_buffer8->reserveInitialCapacity(m_length + std::max(addedSize, initialBufferSize()));
haraken 2016/07/01 02:01:03 I don't quite see any reason you want to take std:
m_length = 0;
// Must keep a ref to the string since append will clear it.
String string(m_string);
append(string);
}
-void StringBuilder::createBuffer16()
+void StringBuilder::createBuffer16(unsigned addedSize)
{
DCHECK(m_is8Bit || !hasBuffer());
Buffer8 buffer8;
@@ -145,6 +152,8 @@ void StringBuilder::createBuffer16()
delete m_buffer8;
}
m_buffer16 = new Buffer16;
+ // See createBuffer8's call to reserveInitialCapacity for why we do this.
+ m_buffer16->reserveInitialCapacity(m_length + std::max(addedSize, initialBufferSize()));
m_is8Bit = false;
m_length = 0;
if (!buffer8.isEmpty()) {
@@ -169,7 +178,7 @@ void StringBuilder::append(const UChar* characters, unsigned length)
return;
}
- ensureBuffer16();
+ ensureBuffer16(length);
m_string = String();
m_buffer16->append(characters, length);
m_length += length;
@@ -182,14 +191,14 @@ void StringBuilder::append(const LChar* characters, unsigned length)
DCHECK(characters);
if (m_is8Bit) {
- ensureBuffer8();
+ ensureBuffer8(length);
m_string = String();
m_buffer8->append(characters, length);
m_length += length;
return;
}
- ensureBuffer16();
+ ensureBuffer16(length);
m_string = String();
m_buffer16->reserveCapacity(m_buffer16->size() + length);
for (size_t i = 0; i < length; ++i)

Powered by Google App Engine
This is Rietveld 408576698