Diff
Modified: trunk/Source/WebCore/ChangeLog (135617 => 135618)
--- trunk/Source/WebCore/ChangeLog 2012-11-23 16:38:13 UTC (rev 135617)
+++ trunk/Source/WebCore/ChangeLog 2012-11-23 16:40:33 UTC (rev 135618)
@@ -1,3 +1,25 @@
+2012-11-23 Carlos Garcia Campos <[email protected]>
+
+ [ENCHANT] Infinite loop when end word position is not found
+ https://bugs.webkit.org/show_bug.cgi?id=103139
+
+ Reviewed by Martin Robinson.
+
+ Covered by existing tests in editing/spelling.
+
+ * editing/visible_units.cpp:
+ (WebCore::isLogicalStartOfWord): Make it private again.
+ (WebCore::islogicalEndOfWord): Ditto.
+ * editing/visible_units.h:
+ * platform/text/enchant/TextCheckerEnchant.cpp:
+ (WebCore::TextCheckerEnchant::checkSpellingOfWord): Helper funtion
+ to check a word inside a string using the loaded dictionaries.
+ (WebCore::TextCheckerEnchant::checkSpellingOfString): Optimize and
+ simply the code by using the word iterator to iterate the
+ words.
+ * platform/text/enchant/TextCheckerEnchant.h:
+ (TextCheckerEnchant):
+
2012-11-23 Zeno Albisser <[email protected]>
[Qt] GraphicsContext3DQt makes wrong surface current.
Modified: trunk/Source/WebCore/editing/visible_units.cpp (135617 => 135618)
--- trunk/Source/WebCore/editing/visible_units.cpp 2012-11-23 16:38:13 UTC (rev 135617)
+++ trunk/Source/WebCore/editing/visible_units.cpp 2012-11-23 16:40:33 UTC (rev 135618)
@@ -322,7 +322,7 @@
return wordBreakIterator(string.data(), len);
}
-bool isLogicalStartOfWord(TextBreakIterator* iter, int position, bool hardLineBreak)
+static bool isLogicalStartOfWord(TextBreakIterator* iter, int position, bool hardLineBreak)
{
bool boundary = hardLineBreak ? true : isTextBreak(iter, position);
if (!boundary)
@@ -333,7 +333,7 @@
return isWordTextBreak(iter);
}
-bool islogicalEndOfWord(TextBreakIterator* iter, int position, bool hardLineBreak)
+static bool islogicalEndOfWord(TextBreakIterator* iter, int position, bool hardLineBreak)
{
bool boundary = isTextBreak(iter, position);
return (hardLineBreak || boundary) && isWordTextBreak(iter);
Modified: trunk/Source/WebCore/editing/visible_units.h (135617 => 135618)
--- trunk/Source/WebCore/editing/visible_units.h 2012-11-23 16:38:13 UTC (rev 135617)
+++ trunk/Source/WebCore/editing/visible_units.h 2012-11-23 16:40:33 UTC (rev 135618)
@@ -46,9 +46,6 @@
VisiblePosition rightWordPosition(const VisiblePosition&, bool skipsSpaceWhenMovingRight);
VisiblePosition leftWordPosition(const VisiblePosition&, bool skipsSpaceWhenMovingRight);
bool isStartOfWord(const VisiblePosition&);
-// used by TextCheckerEnchant.cpp
-bool isLogicalStartOfWord(TextBreakIterator*, int position, bool hardLineBreak = false);
-bool islogicalEndOfWord(TextBreakIterator*, int position, bool hardLineBreak = false);
// sentences
VisiblePosition startOfSentence(const VisiblePosition &);
Modified: trunk/Source/WebCore/platform/text/enchant/TextCheckerEnchant.cpp (135617 => 135618)
--- trunk/Source/WebCore/platform/text/enchant/TextCheckerEnchant.cpp 2012-11-23 16:38:13 UTC (rev 135617)
+++ trunk/Source/WebCore/platform/text/enchant/TextCheckerEnchant.cpp 2012-11-23 16:40:33 UTC (rev 135618)
@@ -23,13 +23,10 @@
#if ENABLE(SPELLCHECK)
#include <Language.h>
-#include <editing/visible_units.h>
#include <glib.h>
#include <text/TextBreakIterator.h>
-#include <wtf/text/CString.h>
-#include <wtf/text/StringBuilder.h>
-using namespace WebCore;
+namespace WebCore {
static const size_t maximumNumberOfSuggestions = 10;
@@ -66,6 +63,25 @@
enchant_dict_add_to_personal(*iter, word.utf8().data(), -1);
}
+void TextCheckerEnchant::checkSpellingOfWord(const CString& word, int start, int end, int& misspellingLocation, int& misspellingLength)
+{
+ const char* string = word.data();
+ char* startPtr = g_utf8_offset_to_pointer(string, start);
+ int numberOfBytes = static_cast<int>(g_utf8_offset_to_pointer(string, end) - startPtr);
+
+ for (Vector<EnchantDict*>::const_iterator dictIter = m_enchantDictionaries.begin(); dictIter != m_enchantDictionaries.end(); ++dictIter) {
+ if (!enchant_dict_check(*dictIter, startPtr, numberOfBytes)) {
+ // Stop checking, this word is ok in at least one dict.
+ misspellingLocation = -1;
+ misspellingLength = 0;
+ break;
+ }
+
+ misspellingLocation = start;
+ misspellingLength = end - start;
+ }
+}
+
void TextCheckerEnchant::checkSpellingOfString(const String& string, int& misspellingLocation, int& misspellingLength)
{
// Assume that the words in the string are spelled correctly.
@@ -75,46 +91,16 @@
if (!hasDictionary())
return;
- size_t numberOfCharacters = string.length();
- TextBreakIterator* iter = wordBreakIterator(string.characters(), numberOfCharacters);
+ TextBreakIterator* iter = wordBreakIterator(string.characters(), string.length());
if (!iter)
return;
CString utf8String = string.utf8();
- const char* cString = utf8String.data();
-
- for (size_t i = 0; i < numberOfCharacters + 1; i++) {
- // We go through each character until we find the beginning of the word
- // then we get into an inner loop to find the end of the word corresponding
- // to it.
- if (isLogicalStartOfWord(iter, i)) {
- int start = i;
- int end = i;
- int wordLength;
-
- while (!islogicalEndOfWord(iter, end))
- end++;
-
- wordLength = end - start;
- // Set the iterator to be at the current word end, so we don't
- // check characters twice.
- i = end;
-
- char* cstart = g_utf8_offset_to_pointer(cString, start);
- int numberOfBytes = static_cast<int>(g_utf8_offset_to_pointer(cString, end) - cstart);
-
- for (Vector<EnchantDict*>::const_iterator dictIter = m_enchantDictionaries.begin(); dictIter != m_enchantDictionaries.end(); ++dictIter) {
- if (enchant_dict_check(*dictIter, cstart, numberOfBytes)) {
- misspellingLocation = start;
- misspellingLength = wordLength;
- } else {
- // Stop checking, this word is ok in at least one dict.
- misspellingLocation = -1;
- misspellingLength = 0;
- break;
- }
- }
- }
+ int start = textBreakFirst(iter);
+ for (int end = textBreakNext(iter); end != TextBreakDone; end = textBreakNext(iter)) {
+ if (isWordTextBreak(iter))
+ checkSpellingOfWord(utf8String, start, end, misspellingLocation, misspellingLength);
+ start = end;
}
}
@@ -212,5 +198,7 @@
enchant_broker_free_dict(m_broker, *iter);
}
+} // namespace WebCore
+
#endif // ENABLE(SPELLCHECK)
Modified: trunk/Source/WebCore/platform/text/enchant/TextCheckerEnchant.h (135617 => 135618)
--- trunk/Source/WebCore/platform/text/enchant/TextCheckerEnchant.h 2012-11-23 16:38:13 UTC (rev 135617)
+++ trunk/Source/WebCore/platform/text/enchant/TextCheckerEnchant.h 2012-11-23 16:40:33 UTC (rev 135618)
@@ -26,6 +26,7 @@
#include <wtf/FastAllocBase.h>
#include <wtf/PassOwnPtr.h>
#include <wtf/Vector.h>
+#include <wtf/text/CString.h>
#include <wtf/text/WTFString.h>
namespace WebCore {
@@ -49,6 +50,7 @@
private:
TextCheckerEnchant();
void freeEnchantBrokerDictionaries();
+ void checkSpellingOfWord(const CString&, int start, int end, int& misspellingLocation, int& misspellingLength);
EnchantBroker* m_broker;
Vector<EnchantDict*> m_enchantDictionaries;