Fix a crash when MAX_WORD_LENGTH is too short.
Change-Id: Idcb5aa2685321b8d0ac7d846caecbd1c79e4dd77
diff --git a/java/src/com/android/inputmethod/latin/BinaryDictionary.java b/java/src/com/android/inputmethod/latin/BinaryDictionary.java
index c7f629f..961b49f 100644
--- a/java/src/com/android/inputmethod/latin/BinaryDictionary.java
+++ b/java/src/com/android/inputmethod/latin/BinaryDictionary.java
@@ -170,12 +170,12 @@
mOutputChars_bigrams, mFrequencies_bigrams, MAX_WORD_LENGTH, MAX_BIGRAMS,
MAX_ALTERNATIVES);
- for (int j = 0; j < count; j++) {
+ for (int j = 0; j < count; ++j) {
if (mFrequencies_bigrams[j] < 1) break;
- int start = j * MAX_WORD_LENGTH;
+ final int start = j * MAX_WORD_LENGTH;
int len = 0;
- while (mOutputChars_bigrams[start + len] != 0) {
- len++;
+ while (len < MAX_WORD_LENGTH && mOutputChars_bigrams[start + len] != 0) {
+ ++len;
}
if (len > 0) {
callback.addWord(mOutputChars_bigrams, start, len, mFrequencies_bigrams[j],
@@ -204,12 +204,12 @@
mFrequencies, nextLettersFrequencies,
nextLettersFrequencies != null ? nextLettersFrequencies.length : 0);
- for (int j = 0; j < count; j++) {
+ for (int j = 0; j < count; ++j) {
if (mFrequencies[j] < 1) break;
- int start = j * MAX_WORD_LENGTH;
+ final int start = j * MAX_WORD_LENGTH;
int len = 0;
- while (mOutputChars[start + len] != 0) {
- len++;
+ while (len < MAX_WORD_LENGTH && mOutputChars[start + len] != 0) {
+ ++len;
}
if (len > 0) {
callback.addWord(mOutputChars, start, len, mFrequencies[j], mDicTypeId,
diff --git a/native/src/bigram_dictionary.cpp b/native/src/bigram_dictionary.cpp
index 095b805..7bfef38 100644
--- a/native/src/bigram_dictionary.cpp
+++ b/native/src/bigram_dictionary.cpp
@@ -146,7 +146,7 @@
bool firstAddress = true;
bool haveToSearchAll = true;
- if (depth >= 0) {
+ if (depth < MAX_WORD_LENGTH && depth >= 0) {
word[depth] = (unsigned short) followingChar;
}
pos = followDownBranchAddress; // pos start at count
diff --git a/native/src/defines.h b/native/src/defines.h
index 953905f..8b817fb 100644
--- a/native/src/defines.h
+++ b/native/src/defines.h
@@ -50,8 +50,12 @@
#define SUGGEST_MISSING_CHARACTERS true
#define SUGGEST_MISSING_CHARACTERS_THRESHOLD 5
-#define MAX_WORD_LENGTH_INTERNAL 64
+// This should be greater than or equal to MAX_WORD_LENGTH defined in BinaryDictionary.java
+// This is only used for the size of array. Not to be used in c functions.
+#define MAX_WORD_LENGTH_INTERNAL 48
#define MAX_DEPTH_MULTIPLIER 3
+#define min(a,b) ((a)<(b)?(a):(b))
+
#endif // LATINIME_DEFINES_H
diff --git a/native/src/unigram_dictionary.cpp b/native/src/unigram_dictionary.cpp
index fa4e296..707f1e6 100644
--- a/native/src/unigram_dictionary.cpp
+++ b/native/src/unigram_dictionary.cpp
@@ -16,8 +16,8 @@
*/
#include <assert.h>
-#include <stdio.h>
#include <fcntl.h>
+#include <stdio.h>
#include <string.h>
#define LOG_TAG "LatinIME: unigram_dictionary.cpp"
@@ -78,6 +78,7 @@
void UnigramDictionary::initSuggestions(int *codes, int codesSize, unsigned short *outWords,
int *frequencies) {
+ if (DEBUG_DICT) LOGI("initSuggest");
mFrequencies = frequencies;
mOutputChars = outWords;
mInputCodes = codes;
@@ -87,6 +88,7 @@
int UnigramDictionary::getSuggestionCandidates(int inputLength, int skipPos,
int *nextLetters, int nextLettersSize) {
+ if (DEBUG_DICT) LOGI("getSuggestionCandidates");
int initialPos = 0;
if (IS_LATEST_DICT_VERSION) {
initialPos = DICTIONARY_HEADER_SIZE;
@@ -115,6 +117,10 @@
for (int i = 0; i <= length; i++) s[i] = word[i];
LOGI("Found word = %s, freq = %d : \n", s, frequency);
}
+ if (length > MAX_WORD_LENGTH) {
+ if (DEBUG_DICT) LOGI("Exceeded max word length.");
+ return false;
+ }
// Find the right insertion point
int insertAt = 0;
@@ -177,7 +183,8 @@
int *nextLetters, const int nextLettersSize) {
int initialPosition = initialPos;
const int count = Dictionary::getCount(DICT, &initialPosition);
- getWordsRec(count, initialPosition, 0, inputLength * MAX_DEPTH_MULTIPLIER,
+ getWordsRec(count, initialPosition, 0,
+ min(inputLength * MAX_DEPTH_MULTIPLIER, MAX_WORD_LENGTH),
mInputLength <= 0, 1, 0, 0, skipPos, nextLetters, nextLettersSize);
}