Diff
Modified: trunk/Source/WebCore/ChangeLog (135971 => 135972)
--- trunk/Source/WebCore/ChangeLog 2012-11-28 05:24:15 UTC (rev 135971)
+++ trunk/Source/WebCore/ChangeLog 2012-11-28 05:27:34 UTC (rev 135972)
@@ -1,3 +1,33 @@
+2012-11-27 Michael Saboff <msab...@apple.com>
+
+ TextIterator unnecessarily converts 8 bit strings to 16 bits
+ https://bugs.webkit.org/show_bug.cgi?id=103295
+
+ Reviewed by Brent Fulgham.
+
+ Changed TextIterator to use the contained string instead of calling characters() on that string.
+ Other sources of text, like emitCharacter() still use the contained UChar* buffer.
+ Added appendTextToStringBuilder() to append the text contents of the current iterator to a string builder
+ irrespective of the source of the text.
+
+ No new tests as functionality covered by existing tests.
+
+ * WebCore.exp.in: Updated plainText export and eliminated plainTextToMallocAllocatedBuffer export
+ * accessibility/AccessibilityObject.cpp:
+ (WebCore::AccessibilityObject::stringForVisiblePositionRange): Updated to use TextIterator::appendTextToStringBuilder()
+ * editing/TextIterator.cpp:
+ (WebCore::TextIterator::characterAt): New function to return the indexed character of the current TextIterator
+ (WebCore::TextIterator::appendTextToStringBuilder): Added method to append whatever the current text to a StringBuilder
+ (WebCore::TextIterator::emitText): Eliminated accessing the character data via characters().
+ (WebCore::TextIterator::rangeFromLocationAndLength): Changed to use characterAt().
+ (WebCore::plainText): Combined with plainTextToMallocAllocatedBuffer().
+ * editing/TextIterator.h:
+ (WebCore::TextIterator::startOffset): New getter.
+ (WebCore::TextIterator::string): New getter.
+ (WebCore::TextIterator::characters): Updated to use correct test source.
+ * page/ContextMenuController.cpp:
+ (WebCore::selectionContainsPossibleWord): Changed to use characterAt().
+
2012-11-27 Noel Gordon <noel.gor...@gmail.com>
Inline ImageFrame width() and height()
Modified: trunk/Source/WebCore/WebCore.exp.in (135971 => 135972)
--- trunk/Source/WebCore/WebCore.exp.in 2012-11-28 05:24:15 UTC (rev 135971)
+++ trunk/Source/WebCore/WebCore.exp.in 2012-11-28 05:27:34 UTC (rev 135972)
@@ -691,7 +691,6 @@
__ZN7WebCore30overrideUserPreferredLanguagesERKN3WTF6VectorINS0_6StringELm0EEE
__ZN7WebCore31CrossOriginPreflightResultCache5emptyEv
__ZN7WebCore31CrossOriginPreflightResultCache6sharedEv
-__ZN7WebCore32plainTextToMallocAllocatedBufferEPKNS_5RangeERjbNS_20TextIteratorBehaviorE
__ZN7WebCore33stripLeadingAndTrailingHTMLSpacesERKN3WTF6StringE
__ZN7WebCore37WidgetHierarchyUpdatesSuspensionScope11moveWidgetsEv
__ZN7WebCore37WidgetHierarchyUpdatesSuspensionScope35s_widgetHierarchyUpdateSuspendCountE
@@ -1094,7 +1093,7 @@
__ZN7WebCore9fontCacheEv
__ZN7WebCore9makeRangeERKNS_15VisiblePositionES2_
__ZN7WebCore9pageCacheEv
-__ZN7WebCore9plainTextEPKNS_5RangeENS_20TextIteratorBehaviorE
+__ZN7WebCore9plainTextEPKNS_5RangeENS_20TextIteratorBehaviorEb
__ZN7WebCore9toElementEN3JSC7JSValueE
__ZN7WebCore9unionRectERKN3WTF6VectorINS_9FloatRectELm0EEE
__ZNK3JSC8Bindings10RootObject12globalObjectEv
Modified: trunk/Source/WebCore/accessibility/AccessibilityObject.cpp (135971 => 135972)
--- trunk/Source/WebCore/accessibility/AccessibilityObject.cpp 2012-11-28 05:24:15 UTC (rev 135971)
+++ trunk/Source/WebCore/accessibility/AccessibilityObject.cpp 2012-11-28 05:27:34 UTC (rev 135972)
@@ -840,7 +840,7 @@
if (!listMarkerText.isEmpty())
builder.append(listMarkerText);
- builder.append(it.characters(), it.length());
+ it.appendTextToStringBuilder(builder);
} else {
// locate the node and starting offset for this replaced range
int exception = 0;
Modified: trunk/Source/WebCore/editing/TextIterator.cpp (135971 => 135972)
--- trunk/Source/WebCore/editing/TextIterator.cpp 2012-11-28 05:24:15 UTC (rev 135971)
+++ trunk/Source/WebCore/editing/TextIterator.cpp 2012-11-28 05:27:34 UTC (rev 135972)
@@ -462,6 +462,26 @@
}
}
+UChar TextIterator::characterAt(unsigned index) const
+{
+ ASSERT(index < static_cast<unsigned>(length()));
+ if (!(index < static_cast<unsigned>(length())))
+ return 0;
+
+ if (!m_textCharacters)
+ return string()[startOffset() + index];
+
+ return m_textCharacters[index];
+}
+
+void TextIterator::appendTextToStringBuilder(StringBuilder& builder) const
+{
+ if (!m_textCharacters)
+ builder.append(string(), startOffset(), length());
+ else
+ builder.append(characters(), length());
+}
+
bool TextIterator::handleTextNode()
{
if (m_fullyClippedStack.top() && !m_ignoresStyleVisibility)
@@ -1007,7 +1027,7 @@
{
RenderText* renderer = toRenderText(renderObject);
m_text = m_emitsOriginalText ? renderer->originalText() : (m_emitsTextWithoutTranscoding ? renderer->textWithoutTranscoding() : renderer->text());
- ASSERT(m_text.characters());
+ ASSERT(!m_text.isEmpty());
ASSERT(0 <= textStartOffset && textStartOffset < static_cast<int>(m_text.length()));
ASSERT(0 <= textEndOffset && textEndOffset <= static_cast<int>(m_text.length()));
ASSERT(textStartOffset <= textEndOffset);
@@ -1016,7 +1036,7 @@
m_positionOffsetBaseNode = 0;
m_positionStartOffset = textStartOffset;
m_positionEndOffset = textEndOffset;
- m_textCharacters = m_text.characters() + textStartOffset;
+ m_textCharacters = 0;
m_textLength = textEndOffset - textStartOffset;
m_lastCharacter = m_text[textEndOffset - 1];
@@ -2439,7 +2459,7 @@
if (foundEnd) {
// FIXME: This is a workaround for the fact that the end of a run is often at the wrong
// position for emitted '\n's.
- if (len == 1 && it.characters()[0] == '\n') {
+ if (len == 1 && it.characterAt(0) == '\n') {
scope->document()->updateLayoutIgnorePendingStylesheets();
it.advance();
if (!it.atEnd()) {
@@ -2531,82 +2551,38 @@
}
// --------
-
-UChar* plainTextToMallocAllocatedBuffer(const Range* r, unsigned& bufferLength, bool isDisplayString, TextIteratorBehavior defaultBehavior)
-{
- UChar* result = 0;
+String plainText(const Range* r, TextIteratorBehavior defaultBehavior, bool isDisplayString)
+{
// The initial buffer size can be critical for performance: https://bugs.webkit.org/show_bug.cgi?id=81192
static const unsigned cMaxSegmentSize = 1 << 15;
- bufferLength = 0;
- typedef pair<UChar*, unsigned> TextSegment;
- OwnPtr<Vector<TextSegment> > textSegments;
- Vector<UChar> textBuffer;
- textBuffer.reserveInitialCapacity(cMaxSegmentSize);
+
+ unsigned bufferLength = 0;
+ StringBuilder builder;
+ builder.reserveCapacity(cMaxSegmentSize);
TextIteratorBehavior behavior = defaultBehavior;
if (!isDisplayString)
behavior = static_cast<TextIteratorBehavior>(behavior | TextIteratorEmitsTextsWithoutTranscoding);
for (TextIterator it(r, behavior); !it.atEnd(); it.advance()) {
- if (textBuffer.size() && textBuffer.size() + it.length() > cMaxSegmentSize) {
- UChar* newSegmentBuffer = static_cast<UChar*>(malloc(textBuffer.size() * sizeof(UChar)));
- if (!newSegmentBuffer)
- goto exit;
- memcpy(newSegmentBuffer, textBuffer.data(), textBuffer.size() * sizeof(UChar));
- if (!textSegments)
- textSegments = adoptPtr(new Vector<TextSegment>);
- textSegments->append(make_pair(newSegmentBuffer, (unsigned)textBuffer.size()));
- textBuffer.clear();
- }
- textBuffer.append(it.characters(), it.length());
+ if (builder.capacity() < builder.length() + it.length())
+ builder.reserveCapacity(builder.capacity() + cMaxSegmentSize);
+
+ it.appendTextToStringBuilder(builder);
bufferLength += it.length();
}
if (!bufferLength)
- return 0;
+ return emptyString();
- // Since we know the size now, we can make a single buffer out of the pieces with one big alloc
- result = static_cast<UChar*>(malloc(bufferLength * sizeof(UChar)));
- if (!result)
- goto exit;
+ String result = builder.toString();
- {
- UChar* resultPos = result;
- if (textSegments) {
- unsigned size = textSegments->size();
- for (unsigned i = 0; i < size; ++i) {
- const TextSegment& segment = textSegments->at(i);
- memcpy(resultPos, segment.first, segment.second * sizeof(UChar));
- resultPos += segment.second;
- }
- }
- memcpy(resultPos, textBuffer.data(), textBuffer.size() * sizeof(UChar));
- }
-
-exit:
- if (textSegments) {
- unsigned size = textSegments->size();
- for (unsigned i = 0; i < size; ++i)
- free(textSegments->at(i).first);
- }
-
if (isDisplayString && r->ownerDocument())
- r->ownerDocument()->displayBufferModifiedByEncoding(result, bufferLength);
+ r->ownerDocument()->displayStringModifiedByEncoding(result);
return result;
}
-String plainText(const Range* r, TextIteratorBehavior defaultBehavior)
-{
- unsigned length;
- UChar* buf = plainTextToMallocAllocatedBuffer(r, length, false, defaultBehavior);
- if (!buf)
- return "";
- String result(buf, length);
- free(buf);
- return result;
-}
-
static inline bool isAllCollapsibleWhitespace(const String& string)
{
const UChar* characters = string.characters();
Modified: trunk/Source/WebCore/editing/TextIterator.h (135971 => 135972)
--- trunk/Source/WebCore/editing/TextIterator.h 2012-11-28 05:24:15 UTC (rev 135971)
+++ trunk/Source/WebCore/editing/TextIterator.h 2012-11-28 05:27:34 UTC (rev 135972)
@@ -60,8 +60,7 @@
}
}
-String plainText(const Range*, TextIteratorBehavior defaultBehavior = TextIteratorDefaultBehavior);
-UChar* plainTextToMallocAllocatedBuffer(const Range*, unsigned& bufferLength, bool isDisplayString, TextIteratorBehavior = TextIteratorDefaultBehavior);
+String plainText(const Range*, TextIteratorBehavior defaultBehavior = TextIteratorDefaultBehavior, bool isDisplayString = false);
PassRefPtr<Range> findPlainText(const Range*, const String&, FindOptions);
class BitStack {
@@ -94,7 +93,9 @@
void advance();
int length() const { return m_textLength; }
- const UChar* characters() const { return m_textCharacters; }
+ const UChar* characters() const { return m_textCharacters ? m_textCharacters : m_text.characters() + startOffset(); }
+ UChar characterAt(unsigned index) const;
+ void appendTextToStringBuilder(StringBuilder&) const;
PassRefPtr<Range> range() const;
Node* node() const;
@@ -105,6 +106,8 @@
static PassRefPtr<Range> subrange(Range* entireRange, int characterOffset, int characterCount);
private:
+ int startOffset() const { return m_positionStartOffset; }
+ const String& string() const { return m_text; }
void exitNode();
bool shouldRepresentNodeOffsetZero();
bool shouldEmitSpaceBeforeAndAfterNode(Node*);
@@ -139,7 +142,7 @@
mutable Node* m_positionOffsetBaseNode;
mutable int m_positionStartOffset;
mutable int m_positionEndOffset;
- const UChar* m_textCharacters;
+ const UChar* m_textCharacters; // If null, then use m_text for character data.
int m_textLength;
// Hold string m_textCharacters points to so we ensure it won't be deleted.
String m_text;
Modified: trunk/Source/WebCore/page/ContextMenuController.cpp (135971 => 135972)
--- trunk/Source/WebCore/page/ContextMenuController.cpp 2012-11-28 05:24:15 UTC (rev 135971)
+++ trunk/Source/WebCore/page/ContextMenuController.cpp 2012-11-28 05:27:34 UTC (rev 135972)
@@ -702,9 +702,8 @@
// Current algorithm: look for a character that's not just a separator.
for (TextIterator it(frame->selection()->toNormalizedRange().get()); !it.atEnd(); it.advance()) {
int length = it.length();
- const UChar* characters = it.characters();
for (int i = 0; i < length; ++i)
- if (!(category(characters[i]) & (Separator_Space | Separator_Line | Separator_Paragraph)))
+ if (!(category(it.characterAt(i)) & (Separator_Space | Separator_Line | Separator_Paragraph)))
return true;
}
return false;
Modified: trunk/Source/WebKit/mac/ChangeLog (135971 => 135972)
--- trunk/Source/WebKit/mac/ChangeLog 2012-11-28 05:24:15 UTC (rev 135971)
+++ trunk/Source/WebKit/mac/ChangeLog 2012-11-28 05:27:34 UTC (rev 135972)
@@ -1,3 +1,15 @@
+2012-11-27 Michael Saboff <msab...@apple.com>
+
+ TextIterator unnecessarily converts 8 bit strings to 16 bits
+ https://bugs.webkit.org/show_bug.cgi?id=103295
+
+ Reviewed by Brent Fulgham.
+
+ Updated _stringForRange to use plainText() instead of removed plainTextToMallocAllocatedBuffer().
+
+ * WebView/WebFrame.mm:
+ (-[WebFrame _stringForRange:]):
+
2012-11-27 James Simonsen <simon...@chromium.org>
Consolidate FrameLoader::load() into one function taking a FrameLoadRequest
Modified: trunk/Source/WebKit/mac/WebView/WebFrame.mm (135971 => 135972)
--- trunk/Source/WebKit/mac/WebView/WebFrame.mm 2012-11-28 05:24:15 UTC (rev 135971)
+++ trunk/Source/WebKit/mac/WebView/WebFrame.mm 2012-11-28 05:27:34 UTC (rev 135972)
@@ -498,15 +498,7 @@
- (NSString *)_stringForRange:(DOMRange *)range
{
- // This will give a system malloc'd buffer that can be turned directly into an NSString
- unsigned length;
- UChar* buf = plainTextToMallocAllocatedBuffer(core(range), length, true);
-
- if (!buf)
- return [NSString string];
-
- // Transfer buffer ownership to NSString
- return [[[NSString alloc] initWithCharactersNoCopy:buf length:length freeWhenDone:YES] autorelease];
+ return plainText(core(range), TextIteratorDefaultBehavior, true);
}
- (BOOL)_shouldFlattenCompositingLayers:(CGContextRef)context