mirror of
https://github.com/unicode-org/icu.git
synced 2025-04-13 08:53:20 +00:00
ICU-5261 Allow the error code to be passed by parameter instead of within the object.
X-SVN-Rev: 19839
This commit is contained in:
parent
46d9f5589d
commit
2d277e543c
2 changed files with 102 additions and 108 deletions
|
@ -279,8 +279,6 @@ public:
|
|||
|
||||
UBool anchorStart;
|
||||
UBool anchorEnd;
|
||||
|
||||
UErrorCode ec;
|
||||
|
||||
/**
|
||||
* The segment number from 1..n of the next '(' we see
|
||||
|
@ -296,12 +294,13 @@ public:
|
|||
RuleHalf(TransliteratorParser& parser);
|
||||
~RuleHalf();
|
||||
|
||||
int32_t parse(const UnicodeString& rule, int32_t pos, int32_t limit);
|
||||
int32_t parse(const UnicodeString& rule, int32_t pos, int32_t limit, UErrorCode& status);
|
||||
|
||||
int32_t parseSection(const UnicodeString& rule, int32_t pos, int32_t limit,
|
||||
UnicodeString& buf,
|
||||
const UnicodeString& illegal,
|
||||
UBool isSegment);
|
||||
UBool isSegment,
|
||||
UErrorCode& status);
|
||||
|
||||
/**
|
||||
* Remove context.
|
||||
|
@ -322,8 +321,9 @@ public:
|
|||
|
||||
int syntaxError(UErrorCode code,
|
||||
const UnicodeString& rule,
|
||||
int32_t start) {
|
||||
return parser.syntaxError(code, rule, start);
|
||||
int32_t start,
|
||||
UErrorCode& status) {
|
||||
return parser.syntaxError(code, rule, start, status);
|
||||
}
|
||||
|
||||
private:
|
||||
|
@ -333,7 +333,6 @@ private:
|
|||
};
|
||||
|
||||
RuleHalf::RuleHalf(TransliteratorParser& p) :
|
||||
ec(U_ZERO_ERROR),
|
||||
parser(p)
|
||||
{
|
||||
cursor = -1;
|
||||
|
@ -354,13 +353,13 @@ RuleHalf::~RuleHalf() {
|
|||
* @return the index after the terminating character, or
|
||||
* if limit was reached, limit
|
||||
*/
|
||||
int32_t RuleHalf::parse(const UnicodeString& rule, int32_t pos, int32_t limit) {
|
||||
int32_t RuleHalf::parse(const UnicodeString& rule, int32_t pos, int32_t limit, UErrorCode& status) {
|
||||
int32_t start = pos;
|
||||
text.truncate(0);
|
||||
pos = parseSection(rule, pos, limit, text, ILLEGAL_TOP, FALSE);
|
||||
pos = parseSection(rule, pos, limit, text, ILLEGAL_TOP, FALSE, status);
|
||||
|
||||
if (cursorOffset > 0 && cursor != cursorOffsetPos) {
|
||||
return syntaxError(U_MISPLACED_CURSOR_OFFSET, rule, start);
|
||||
return syntaxError(U_MISPLACED_CURSOR_OFFSET, rule, start, status);
|
||||
}
|
||||
|
||||
return pos;
|
||||
|
@ -392,7 +391,7 @@ int32_t RuleHalf::parse(const UnicodeString& rule, int32_t pos, int32_t limit) {
|
|||
int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t limit,
|
||||
UnicodeString& buf,
|
||||
const UnicodeString& illegal,
|
||||
UBool isSegment) {
|
||||
UBool isSegment, UErrorCode& status) {
|
||||
int32_t start = pos;
|
||||
ParsePosition pp;
|
||||
UnicodeString scratch;
|
||||
|
@ -416,19 +415,19 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
if (u_strchr(HALF_ENDERS, c) != NULL) {
|
||||
if (isSegment) {
|
||||
// Unclosed segment
|
||||
return syntaxError(U_UNCLOSED_SEGMENT, rule, start);
|
||||
return syntaxError(U_UNCLOSED_SEGMENT, rule, start, status);
|
||||
}
|
||||
break;
|
||||
}
|
||||
if (anchorEnd) {
|
||||
// Text after a presumed end anchor is a syntax err
|
||||
return syntaxError(U_MALFORMED_VARIABLE_REFERENCE, rule, start);
|
||||
return syntaxError(U_MALFORMED_VARIABLE_REFERENCE, rule, start, status);
|
||||
}
|
||||
if (UnicodeSet::resemblesPattern(rule, pos-1)) {
|
||||
pp.setIndex(pos-1); // Backup to opening '['
|
||||
buf.append(parser.parseSet(rule, pp));
|
||||
if (U_FAILURE(parser.status)) {
|
||||
return syntaxError(U_MALFORMED_SET, rule, start);
|
||||
buf.append(parser.parseSet(rule, pp, status));
|
||||
if (U_FAILURE(status)) {
|
||||
return syntaxError(U_MALFORMED_SET, rule, start, status);
|
||||
}
|
||||
pos = pp.getIndex();
|
||||
continue;
|
||||
|
@ -436,14 +435,14 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
// Handle escapes
|
||||
if (c == ESCAPE) {
|
||||
if (pos == limit) {
|
||||
return syntaxError(U_TRAILING_BACKSLASH, rule, start);
|
||||
return syntaxError(U_TRAILING_BACKSLASH, rule, start, status);
|
||||
}
|
||||
UChar32 escaped = rule.unescapeAt(pos); // pos is already past '\\'
|
||||
if (escaped == (UChar32) -1) {
|
||||
return syntaxError(U_MALFORMED_UNICODE_ESCAPE, rule, start);
|
||||
return syntaxError(U_MALFORMED_UNICODE_ESCAPE, rule, start, status);
|
||||
}
|
||||
if (!parser.checkVariableRange(escaped)) {
|
||||
return syntaxError(U_VARIABLE_RANGE_OVERLAP, rule, start);
|
||||
return syntaxError(U_VARIABLE_RANGE_OVERLAP, rule, start, status);
|
||||
}
|
||||
buf.append(escaped);
|
||||
continue;
|
||||
|
@ -464,7 +463,7 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
quoteStart = buf.length();
|
||||
for (;;) {
|
||||
if (iq < 0) {
|
||||
return syntaxError(U_UNTERMINATED_QUOTE, rule, start);
|
||||
return syntaxError(U_UNTERMINATED_QUOTE, rule, start, status);
|
||||
}
|
||||
scratch.truncate(0);
|
||||
rule.extractBetween(pos, iq, scratch);
|
||||
|
@ -482,7 +481,7 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
|
||||
for (iq=quoteStart; iq<quoteLimit; ++iq) {
|
||||
if (!parser.checkVariableRange(buf.charAt(iq))) {
|
||||
return syntaxError(U_VARIABLE_RANGE_OVERLAP, rule, start);
|
||||
return syntaxError(U_VARIABLE_RANGE_OVERLAP, rule, start, status);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -490,11 +489,11 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
}
|
||||
|
||||
if (!parser.checkVariableRange(c)) {
|
||||
return syntaxError(U_VARIABLE_RANGE_OVERLAP, rule, start);
|
||||
return syntaxError(U_VARIABLE_RANGE_OVERLAP, rule, start, status);
|
||||
}
|
||||
|
||||
if (illegal.indexOf(c) >= 0) {
|
||||
syntaxError(U_ILLEGAL_CHARACTER, rule, start);
|
||||
syntaxError(U_ILLEGAL_CHARACTER, rule, start, status);
|
||||
}
|
||||
|
||||
switch (c) {
|
||||
|
@ -507,7 +506,7 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
anchorStart = TRUE;
|
||||
} else {
|
||||
return syntaxError(U_MISPLACED_ANCHOR_START,
|
||||
rule, start);
|
||||
rule, start, status);
|
||||
}
|
||||
break;
|
||||
case SEGMENT_OPEN:
|
||||
|
@ -522,7 +521,7 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
int32_t segmentNumber = nextSegmentNumber++; // 1-based
|
||||
|
||||
// Parse the segment
|
||||
pos = parseSection(rule, pos, limit, buf, ILLEGAL_SEG, TRUE);
|
||||
pos = parseSection(rule, pos, limit, buf, ILLEGAL_SEG, TRUE, status);
|
||||
|
||||
// After parsing a segment, the relevant characters are
|
||||
// in buf, starting at offset bufSegStart. Extract them
|
||||
|
@ -533,9 +532,9 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
segmentNumber, *parser.curData);
|
||||
|
||||
// Record and associate object and segment number
|
||||
parser.setSegmentObject(segmentNumber, m);
|
||||
parser.setSegmentObject(segmentNumber, m, status);
|
||||
buf.truncate(bufSegStart);
|
||||
buf.append(parser.getSegmentStandin(segmentNumber));
|
||||
buf.append(parser.getSegmentStandin(segmentNumber, status));
|
||||
}
|
||||
break;
|
||||
case FUNCTION:
|
||||
|
@ -547,13 +546,13 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
// The next character MUST be a segment open
|
||||
if (single == NULL ||
|
||||
!ICU_Utility::parseChar(rule, iref, SEGMENT_OPEN)) {
|
||||
return syntaxError(U_INVALID_FUNCTION, rule, start);
|
||||
return syntaxError(U_INVALID_FUNCTION, rule, start, status);
|
||||
}
|
||||
|
||||
Transliterator *t = single->createInstance();
|
||||
delete single;
|
||||
if (t == NULL) {
|
||||
return syntaxError(U_INVALID_FUNCTION, rule, start);
|
||||
return syntaxError(U_INVALID_FUNCTION, rule, start, status);
|
||||
}
|
||||
|
||||
// bufSegStart is the offset in buf to the first
|
||||
|
@ -561,7 +560,7 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
int32_t bufSegStart = buf.length();
|
||||
|
||||
// Parse the segment
|
||||
pos = parseSection(rule, iref, limit, buf, ILLEGAL_FUNC, TRUE);
|
||||
pos = parseSection(rule, iref, limit, buf, ILLEGAL_FUNC, TRUE, status);
|
||||
|
||||
// After parsing a segment, the relevant characters are
|
||||
// in buf, starting at offset bufSegStart.
|
||||
|
@ -572,7 +571,7 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
|
||||
// Replace the buffer contents with a stand-in
|
||||
buf.truncate(bufSegStart);
|
||||
buf.append(parser.generateStandInFor(r));
|
||||
buf.append(parser.generateStandInFor(r, status));
|
||||
}
|
||||
break;
|
||||
case SymbolTable::SYMBOL_REF:
|
||||
|
@ -595,9 +594,9 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
r = ICU_Utility::parseNumber(rule, pos, 10);
|
||||
if (r < 0) {
|
||||
return syntaxError(U_UNDEFINED_SEGMENT_REFERENCE,
|
||||
rule, start);
|
||||
rule, start, status);
|
||||
}
|
||||
buf.append(parser.getSegmentStandin(r));
|
||||
buf.append(parser.getSegmentStandin(r, status));
|
||||
} else {
|
||||
pp.setIndex(pos);
|
||||
UnicodeString name = parser.parseData->
|
||||
|
@ -617,13 +616,13 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
// that case appendVariableDef() will append the
|
||||
// special placeholder char variableLimit-1.
|
||||
varStart = buf.length();
|
||||
parser.appendVariableDef(name, buf);
|
||||
parser.appendVariableDef(name, buf, status);
|
||||
varLimit = buf.length();
|
||||
}
|
||||
}
|
||||
break;
|
||||
case DOT:
|
||||
buf.append(parser.getDotStandIn());
|
||||
buf.append(parser.getDotStandIn(status));
|
||||
break;
|
||||
case KLEENE_STAR:
|
||||
case ONE_OR_MORE:
|
||||
|
@ -637,7 +636,7 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
{
|
||||
if (isSegment && buf.length() == bufStart) {
|
||||
// The */+ immediately follows '('
|
||||
return syntaxError(U_MISPLACED_QUANTIFIER, rule, start);
|
||||
return syntaxError(U_MISPLACED_QUANTIFIER, rule, start, status);
|
||||
}
|
||||
|
||||
int32_t qstart, qlimit;
|
||||
|
@ -675,7 +674,7 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
}
|
||||
m = new Quantifier(m, min, max);
|
||||
buf.truncate(qstart);
|
||||
buf.append(parser.generateStandInFor(m));
|
||||
buf.append(parser.generateStandInFor(m, status));
|
||||
}
|
||||
break;
|
||||
|
||||
|
@ -693,31 +692,31 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
//------------------------------------------------------
|
||||
case CONTEXT_ANTE:
|
||||
if (ante >= 0) {
|
||||
return syntaxError(U_MULTIPLE_ANTE_CONTEXTS, rule, start);
|
||||
return syntaxError(U_MULTIPLE_ANTE_CONTEXTS, rule, start, status);
|
||||
}
|
||||
ante = buf.length();
|
||||
break;
|
||||
case CONTEXT_POST:
|
||||
if (post >= 0) {
|
||||
return syntaxError(U_MULTIPLE_POST_CONTEXTS, rule, start);
|
||||
return syntaxError(U_MULTIPLE_POST_CONTEXTS, rule, start, status);
|
||||
}
|
||||
post = buf.length();
|
||||
break;
|
||||
case CURSOR_POS:
|
||||
if (cursor >= 0) {
|
||||
return syntaxError(U_MULTIPLE_CURSORS, rule, start);
|
||||
return syntaxError(U_MULTIPLE_CURSORS, rule, start, status);
|
||||
}
|
||||
cursor = buf.length();
|
||||
break;
|
||||
case CURSOR_OFFSET:
|
||||
if (cursorOffset < 0) {
|
||||
if (buf.length() > 0) {
|
||||
return syntaxError(U_MISPLACED_CURSOR_OFFSET, rule, start);
|
||||
return syntaxError(U_MISPLACED_CURSOR_OFFSET, rule, start, status);
|
||||
}
|
||||
--cursorOffset;
|
||||
} else if (cursorOffset > 0) {
|
||||
if (buf.length() != cursorOffsetPos || cursor >= 0) {
|
||||
return syntaxError(U_MISPLACED_CURSOR_OFFSET, rule, start);
|
||||
return syntaxError(U_MISPLACED_CURSOR_OFFSET, rule, start, status);
|
||||
}
|
||||
++cursorOffset;
|
||||
} else {
|
||||
|
@ -727,7 +726,7 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
cursorOffsetPos = buf.length();
|
||||
cursorOffset = 1;
|
||||
} else {
|
||||
return syntaxError(U_MISPLACED_CURSOR_OFFSET, rule, start);
|
||||
return syntaxError(U_MISPLACED_CURSOR_OFFSET, rule, start, status);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
@ -744,7 +743,7 @@ int32_t RuleHalf::parseSection(const UnicodeString& rule, int32_t pos, int32_t l
|
|||
!((c >= 0x0030/*'0'*/ && c <= 0x0039/*'9'*/) ||
|
||||
(c >= 0x0041/*'A'*/ && c <= 0x005A/*'Z'*/) ||
|
||||
(c >= 0x0061/*'a'*/ && c <= 0x007A/*'z'*/))) {
|
||||
return syntaxError(U_UNQUOTED_SPECIAL, rule, start);
|
||||
return syntaxError(U_UNQUOTED_SPECIAL, rule, start, status);
|
||||
}
|
||||
buf.append(c);
|
||||
break;
|
||||
|
@ -808,20 +807,16 @@ UBool RuleHalf::isValidInput(TransliteratorParser& transParser) {
|
|||
* Constructor.
|
||||
*/
|
||||
TransliteratorParser::TransliteratorParser(UErrorCode &statusReturn) :
|
||||
status(U_ZERO_ERROR),
|
||||
dataVector(status),
|
||||
idBlockVector(status),
|
||||
variablesVector(status),
|
||||
segmentObjects(status)
|
||||
dataVector(statusReturn),
|
||||
idBlockVector(statusReturn),
|
||||
variablesVector(statusReturn),
|
||||
segmentObjects(statusReturn)
|
||||
{
|
||||
idBlockVector.setDeleter(uhash_deleteUnicodeString);
|
||||
curData = NULL;
|
||||
compoundFilter = NULL;
|
||||
parseData = NULL;
|
||||
variableNames.setValueDeleter(uhash_deleteUnicodeString);
|
||||
if (U_FAILURE(status)) {
|
||||
statusReturn = status;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -842,9 +837,8 @@ TransliteratorParser::parse(const UnicodeString& rules,
|
|||
UParseError& pe,
|
||||
UErrorCode& ec) {
|
||||
if (U_SUCCESS(ec)) {
|
||||
parseRules(rules, transDirection);
|
||||
parseRules(rules, transDirection, ec);
|
||||
pe = parseError;
|
||||
ec = status;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -870,11 +864,11 @@ UnicodeSet* TransliteratorParser::orphanCompoundFilter() {
|
|||
* rules
|
||||
*/
|
||||
void TransliteratorParser::parseRules(const UnicodeString& rule,
|
||||
UTransDirection theDirection) {
|
||||
UTransDirection theDirection,
|
||||
UErrorCode& status) {
|
||||
// Clear error struct
|
||||
parseError.line = parseError.offset = -1;
|
||||
parseError.preContext[0] = parseError.postContext[0] = (UChar)0;
|
||||
status = U_ZERO_ERROR;
|
||||
|
||||
UBool parsingIDs = TRUE;
|
||||
int32_t ruleCount = 0;
|
||||
|
@ -990,7 +984,7 @@ void TransliteratorParser::parseRules(const UnicodeString& rule,
|
|||
{
|
||||
if (compoundFilter != NULL) {
|
||||
// Multiple compound filters
|
||||
syntaxError(U_MULTIPLE_COMPOUND_FILTERS, rule, pos);
|
||||
syntaxError(U_MULTIPLE_COMPOUND_FILTERS, rule, pos, status);
|
||||
delete f;
|
||||
} else {
|
||||
compoundFilter = f;
|
||||
|
@ -1002,7 +996,7 @@ void TransliteratorParser::parseRules(const UnicodeString& rule,
|
|||
} else {
|
||||
// Invalid ::id
|
||||
// Can be parsed as neither an ID nor a global filter
|
||||
syntaxError(U_INVALID_ID, rule, pos);
|
||||
syntaxError(U_INVALID_ID, rule, pos, status);
|
||||
}
|
||||
}
|
||||
delete id;
|
||||
|
@ -1022,18 +1016,18 @@ void TransliteratorParser::parseRules(const UnicodeString& rule,
|
|||
// E000..F8FF for variables and other stand-ins. Currently
|
||||
// the range F000..F8FF is typically sufficient. The 'use
|
||||
// variable range' pragma allows rule sets to modify this.
|
||||
setVariableRange(0xF000, 0xF8FF);
|
||||
setVariableRange(0xF000, 0xF8FF, status);
|
||||
}
|
||||
|
||||
if (resemblesPragma(rule, pos, limit)) {
|
||||
int32_t ppp = parsePragma(rule, pos, limit);
|
||||
int32_t ppp = parsePragma(rule, pos, limit, status);
|
||||
if (ppp < 0) {
|
||||
syntaxError(U_MALFORMED_PRAGMA, rule, pos);
|
||||
syntaxError(U_MALFORMED_PRAGMA, rule, pos, status);
|
||||
}
|
||||
pos = ppp;
|
||||
// Parse a rule
|
||||
} else {
|
||||
pos = parseRule(rule, pos, limit);
|
||||
pos = parseRule(rule, pos, limit, status);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1101,7 +1095,7 @@ void TransliteratorParser::parseRules(const UnicodeString& rule,
|
|||
/**
|
||||
* Set the variable range to [start, end] (inclusive).
|
||||
*/
|
||||
void TransliteratorParser::setVariableRange(int32_t start, int32_t end) {
|
||||
void TransliteratorParser::setVariableRange(int32_t start, int32_t end, UErrorCode& status) {
|
||||
if (start > end || start < 0 || end > 0xFFFF) {
|
||||
status = U_MALFORMED_PRAGMA;
|
||||
return;
|
||||
|
@ -1169,7 +1163,7 @@ UBool TransliteratorParser::resemblesPragma(const UnicodeString& rule, int32_t p
|
|||
* @return the position index after the final ';' of the pragma,
|
||||
* or -1 on failure.
|
||||
*/
|
||||
int32_t TransliteratorParser::parsePragma(const UnicodeString& rule, int32_t pos, int32_t limit) {
|
||||
int32_t TransliteratorParser::parsePragma(const UnicodeString& rule, int32_t pos, int32_t limit, UErrorCode& status) {
|
||||
int32_t array[2];
|
||||
|
||||
// resemblesPragma() has already returned true, so we
|
||||
|
@ -1184,7 +1178,7 @@ int32_t TransliteratorParser::parsePragma(const UnicodeString& rule, int32_t pos
|
|||
// use nfc rules;
|
||||
int p = ICU_Utility::parsePattern(rule, pos, limit, PRAGMA_VARIABLE_RANGE, array);
|
||||
if (p >= 0) {
|
||||
setVariableRange(array[0], array[1]);
|
||||
setVariableRange(array[0], array[1], status);
|
||||
return p;
|
||||
}
|
||||
|
||||
|
@ -1223,7 +1217,7 @@ int32_t TransliteratorParser::parsePragma(const UnicodeString& rule, int32_t pos
|
|||
* indicators. Once it does a lexical breakdown of the rule at pos, it
|
||||
* creates a rule object and adds it to our rule list.
|
||||
*/
|
||||
int32_t TransliteratorParser::parseRule(const UnicodeString& rule, int32_t pos, int32_t limit) {
|
||||
int32_t TransliteratorParser::parseRule(const UnicodeString& rule, int32_t pos, int32_t limit, UErrorCode& status) {
|
||||
// Locate the left side, operator, and right side
|
||||
int32_t start = pos;
|
||||
UChar op = 0;
|
||||
|
@ -1239,13 +1233,13 @@ int32_t TransliteratorParser::parseRule(const UnicodeString& rule, int32_t pos,
|
|||
RuleHalf* right = &_right;
|
||||
|
||||
undefinedVariableName.remove();
|
||||
pos = left->parse(rule, pos, limit);
|
||||
pos = left->parse(rule, pos, limit, status);
|
||||
if (U_FAILURE(status)) {
|
||||
return start;
|
||||
}
|
||||
|
||||
if (pos == limit || u_strchr(gOPERATORS, (op = rule.charAt(--pos))) == NULL) {
|
||||
return syntaxError(U_MISSING_OPERATOR, rule, start);
|
||||
return syntaxError(U_MISSING_OPERATOR, rule, start, status);
|
||||
}
|
||||
++pos;
|
||||
|
||||
|
@ -1269,7 +1263,7 @@ int32_t TransliteratorParser::parseRule(const UnicodeString& rule, int32_t pos,
|
|||
break;
|
||||
}
|
||||
|
||||
pos = right->parse(rule, pos, limit);
|
||||
pos = right->parse(rule, pos, limit, status);
|
||||
if (U_FAILURE(status)) {
|
||||
return start;
|
||||
}
|
||||
|
@ -1279,7 +1273,7 @@ int32_t TransliteratorParser::parseRule(const UnicodeString& rule, int32_t pos,
|
|||
++pos;
|
||||
} else {
|
||||
// RuleHalf parser must have terminated at an operator
|
||||
return syntaxError(U_UNQUOTED_SPECIAL, rule, start);
|
||||
return syntaxError(U_UNQUOTED_SPECIAL, rule, start, status);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1293,15 +1287,15 @@ int32_t TransliteratorParser::parseRule(const UnicodeString& rule, int32_t pos,
|
|||
// defined).
|
||||
if (undefinedVariableName.length() == 0) {
|
||||
// "Missing '$' or duplicate definition"
|
||||
return syntaxError(U_BAD_VARIABLE_DEFINITION, rule, start);
|
||||
return syntaxError(U_BAD_VARIABLE_DEFINITION, rule, start, status);
|
||||
}
|
||||
if (left->text.length() != 1 || left->text.charAt(0) != variableLimit) {
|
||||
// "Malformed LHS"
|
||||
return syntaxError(U_MALFORMED_VARIABLE_DEFINITION, rule, start);
|
||||
return syntaxError(U_MALFORMED_VARIABLE_DEFINITION, rule, start, status);
|
||||
}
|
||||
if (left->anchorStart || left->anchorEnd ||
|
||||
right->anchorStart || right->anchorEnd) {
|
||||
return syntaxError(U_MALFORMED_VARIABLE_DEFINITION, rule, start);
|
||||
return syntaxError(U_MALFORMED_VARIABLE_DEFINITION, rule, start, status);
|
||||
}
|
||||
// We allow anything on the right, including an empty string.
|
||||
UnicodeString* value = new UnicodeString(right->text);
|
||||
|
@ -1315,21 +1309,21 @@ int32_t TransliteratorParser::parseRule(const UnicodeString& rule, int32_t pos,
|
|||
if (undefinedVariableName.length() != 0) {
|
||||
return syntaxError(// "Undefined variable $" + undefinedVariableName,
|
||||
U_UNDEFINED_VARIABLE,
|
||||
rule, start);
|
||||
rule, start, status);
|
||||
}
|
||||
|
||||
// Verify segments
|
||||
if (segmentStandins.length() > segmentObjects.size()) {
|
||||
syntaxError(U_UNDEFINED_SEGMENT_REFERENCE, rule, start);
|
||||
syntaxError(U_UNDEFINED_SEGMENT_REFERENCE, rule, start, status);
|
||||
}
|
||||
for (i=0; i<segmentStandins.length(); ++i) {
|
||||
if (segmentStandins.charAt(i) == 0) {
|
||||
syntaxError(U_INTERNAL_TRANSLITERATOR_ERROR, rule, start); // will never happen
|
||||
syntaxError(U_INTERNAL_TRANSLITERATOR_ERROR, rule, start, status); // will never happen
|
||||
}
|
||||
}
|
||||
for (i=0; i<segmentObjects.size(); ++i) {
|
||||
if (segmentObjects.elementAt(i) == NULL) {
|
||||
syntaxError(U_INTERNAL_TRANSLITERATOR_ERROR, rule, start); // will never happen
|
||||
syntaxError(U_INTERNAL_TRANSLITERATOR_ERROR, rule, start, status); // will never happen
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1382,7 +1376,7 @@ int32_t TransliteratorParser::parseRule(const UnicodeString& rule, int32_t pos,
|
|||
!left->isValidInput(*this) || !right->isValidOutput(*this) ||
|
||||
left->ante > left->post) {
|
||||
|
||||
return syntaxError(U_MALFORMED_RULE, rule, start);
|
||||
return syntaxError(U_MALFORMED_RULE, rule, start, status);
|
||||
}
|
||||
|
||||
// Flatten segment objects vector to an array
|
||||
|
@ -1414,8 +1408,10 @@ int32_t TransliteratorParser::parseRule(const UnicodeString& rule, int32_t pos,
|
|||
* @param start position of first character of current rule
|
||||
*/
|
||||
int32_t TransliteratorParser::syntaxError(UErrorCode parseErrorCode,
|
||||
const UnicodeString& rule,
|
||||
int32_t pos) {
|
||||
const UnicodeString& rule,
|
||||
int32_t pos,
|
||||
UErrorCode& status)
|
||||
{
|
||||
parseError.offset = pos;
|
||||
parseError.line = 0 ; /* we are not using line numbers */
|
||||
|
||||
|
@ -1446,17 +1442,18 @@ int32_t TransliteratorParser::syntaxError(UErrorCode parseErrorCode,
|
|||
* used to represent it.
|
||||
*/
|
||||
UChar TransliteratorParser::parseSet(const UnicodeString& rule,
|
||||
ParsePosition& pos) {
|
||||
ParsePosition& pos,
|
||||
UErrorCode& status) {
|
||||
UnicodeSet* set = new UnicodeSet(rule, pos, USET_IGNORE_SPACE, parseData, status);
|
||||
set->compact();
|
||||
return generateStandInFor(set);
|
||||
return generateStandInFor(set, status);
|
||||
}
|
||||
|
||||
/**
|
||||
* Generate and return a stand-in for a new UnicodeFunctor. Store
|
||||
* the matcher (adopt it).
|
||||
*/
|
||||
UChar TransliteratorParser::generateStandInFor(UnicodeFunctor* adopted) {
|
||||
UChar TransliteratorParser::generateStandInFor(UnicodeFunctor* adopted, UErrorCode& status) {
|
||||
// assert(obj != null);
|
||||
|
||||
// Look up previous stand-in, if any. This is a short list
|
||||
|
@ -1479,7 +1476,7 @@ UChar TransliteratorParser::generateStandInFor(UnicodeFunctor* adopted) {
|
|||
/**
|
||||
* Return the standin for segment seg (1-based).
|
||||
*/
|
||||
UChar TransliteratorParser::getSegmentStandin(int32_t seg) {
|
||||
UChar TransliteratorParser::getSegmentStandin(int32_t seg, UErrorCode& status) {
|
||||
// Special character used to indicate an empty spot
|
||||
UChar empty = curData->variablesBase - 1;
|
||||
while (segmentStandins.length() < seg) {
|
||||
|
@ -1504,7 +1501,7 @@ UChar TransliteratorParser::getSegmentStandin(int32_t seg) {
|
|||
/**
|
||||
* Set the object for segment seg (1-based).
|
||||
*/
|
||||
void TransliteratorParser::setSegmentObject(int32_t seg, StringMatcher* adopted) {
|
||||
void TransliteratorParser::setSegmentObject(int32_t seg, StringMatcher* adopted, UErrorCode& status) {
|
||||
// Since we call parseSection() recursively, nested
|
||||
// segments will result in segment i+1 getting parsed
|
||||
// and stored before segment i; be careful with the
|
||||
|
@ -1512,7 +1509,7 @@ void TransliteratorParser::setSegmentObject(int32_t seg, StringMatcher* adopted)
|
|||
if (segmentObjects.size() < seg) {
|
||||
segmentObjects.setSize(seg);
|
||||
}
|
||||
int32_t index = getSegmentStandin(seg) - curData->variablesBase;
|
||||
int32_t index = getSegmentStandin(seg, status) - curData->variablesBase;
|
||||
if (segmentObjects.elementAt(seg-1) != NULL ||
|
||||
variablesVector.elementAt(index) != NULL) {
|
||||
// should never happen
|
||||
|
@ -1527,9 +1524,9 @@ void TransliteratorParser::setSegmentObject(int32_t seg, StringMatcher* adopted)
|
|||
* Return the stand-in for the dot set. It is allocated the first
|
||||
* time and reused thereafter.
|
||||
*/
|
||||
UChar TransliteratorParser::getDotStandIn() {
|
||||
UChar TransliteratorParser::getDotStandIn(UErrorCode& status) {
|
||||
if (dotStandIn == (UChar) -1) {
|
||||
dotStandIn = generateStandInFor(new UnicodeSet(DOT_SET, status));
|
||||
dotStandIn = generateStandInFor(new UnicodeSet(DOT_SET, status), status);
|
||||
}
|
||||
return dotStandIn;
|
||||
}
|
||||
|
@ -1539,7 +1536,8 @@ UChar TransliteratorParser::getDotStandIn() {
|
|||
* UnicodeString.
|
||||
*/
|
||||
void TransliteratorParser::appendVariableDef(const UnicodeString& name,
|
||||
UnicodeString& buf) {
|
||||
UnicodeString& buf,
|
||||
UErrorCode& status) {
|
||||
const UnicodeString* s = (const UnicodeString*) variableNames.get(name);
|
||||
if (s == NULL) {
|
||||
// We allow one undefined variable so that variable definition
|
||||
|
|
|
@ -33,14 +33,6 @@ class StringMatcher;
|
|||
|
||||
class TransliteratorParser : public UMemory {
|
||||
|
||||
private:
|
||||
/**
|
||||
* We use a single error code during parsing. Rather than pass it
|
||||
* through each API, we keep it here.
|
||||
* THIS MUST BE DEFINED FIRST!
|
||||
*/
|
||||
UErrorCode status;
|
||||
|
||||
public:
|
||||
|
||||
/**
|
||||
|
@ -185,7 +177,8 @@ private:
|
|||
* @param direction either FORWARD or REVERSE.
|
||||
*/
|
||||
void parseRules(const UnicodeString& rules,
|
||||
UTransDirection direction);
|
||||
UTransDirection direction,
|
||||
UErrorCode& status);
|
||||
|
||||
/**
|
||||
* MAIN PARSER. Parse the next rule in the given rule string, starting
|
||||
|
@ -204,14 +197,14 @@ private:
|
|||
* @param limit pointer past the last character of the rule.
|
||||
* @return the index after the last character parsed.
|
||||
*/
|
||||
int32_t parseRule(const UnicodeString& rule, int32_t pos, int32_t limit);
|
||||
int32_t parseRule(const UnicodeString& rule, int32_t pos, int32_t limit, UErrorCode& status);
|
||||
|
||||
/**
|
||||
* Set the variable range to [start, end] (inclusive).
|
||||
* @param start the start value of the range.
|
||||
* @param end the end value of the range.
|
||||
*/
|
||||
void setVariableRange(int32_t start, int32_t end);
|
||||
void setVariableRange(int32_t start, int32_t end, UErrorCode& status);
|
||||
|
||||
/**
|
||||
* Assert that the given character is NOT within the variable range.
|
||||
|
@ -254,7 +247,7 @@ private:
|
|||
* @return the position index after the final ';' of the pragma,
|
||||
* or -1 on failure.
|
||||
*/
|
||||
int32_t parsePragma(const UnicodeString& rule, int32_t pos, int32_t limit);
|
||||
int32_t parsePragma(const UnicodeString& rule, int32_t pos, int32_t limit, UErrorCode& status);
|
||||
|
||||
/**
|
||||
* Called by main parser upon syntax error. Search the rule string
|
||||
|
@ -266,7 +259,8 @@ private:
|
|||
* @param start position of first character of current rule.
|
||||
* @return start position of first character of current rule.
|
||||
*/
|
||||
int32_t syntaxError(UErrorCode parseErrorCode, const UnicodeString&, int32_t start);
|
||||
int32_t syntaxError(UErrorCode parseErrorCode, const UnicodeString&, int32_t start,
|
||||
UErrorCode& status);
|
||||
|
||||
/**
|
||||
* Parse a UnicodeSet out, store it, and return the stand-in character
|
||||
|
@ -277,7 +271,8 @@ private:
|
|||
* @return the stand-in character used to represent it.
|
||||
*/
|
||||
UChar parseSet(const UnicodeString& rule,
|
||||
ParsePosition& pos);
|
||||
ParsePosition& pos,
|
||||
UErrorCode& status);
|
||||
|
||||
/**
|
||||
* Generate and return a stand-in for a new UnicodeFunctor. Store
|
||||
|
@ -285,28 +280,28 @@ private:
|
|||
* @param adopted the UnicodeFunctor to be adopted.
|
||||
* @return a stand-in for a new UnicodeFunctor.
|
||||
*/
|
||||
UChar generateStandInFor(UnicodeFunctor* adopted);
|
||||
UChar generateStandInFor(UnicodeFunctor* adopted, UErrorCode& status);
|
||||
|
||||
/**
|
||||
* Return the standin for segment seg (1-based).
|
||||
* @param seg the given segment.
|
||||
* @return the standIn character for the given segment.
|
||||
*/
|
||||
UChar getSegmentStandin(int32_t seg);
|
||||
UChar getSegmentStandin(int32_t seg, UErrorCode& status);
|
||||
|
||||
/**
|
||||
* Set the object for segment seg (1-based).
|
||||
* @param seg the given segment.
|
||||
* @param adopted the StringMatcher to be adopted.
|
||||
*/
|
||||
void setSegmentObject(int32_t seg, StringMatcher* adopted);
|
||||
void setSegmentObject(int32_t seg, StringMatcher* adopted, UErrorCode& status);
|
||||
|
||||
/**
|
||||
* Return the stand-in for the dot set. It is allocated the first
|
||||
* time and reused thereafter.
|
||||
* @return the stand-in for the dot set.
|
||||
*/
|
||||
UChar getDotStandIn();
|
||||
UChar getDotStandIn(UErrorCode& status);
|
||||
|
||||
/**
|
||||
* Append the value of the given variable name to the given
|
||||
|
@ -315,7 +310,8 @@ private:
|
|||
* @param buf the given UnicodeString to append to.
|
||||
*/
|
||||
void appendVariableDef(const UnicodeString& name,
|
||||
UnicodeString& buf);
|
||||
UnicodeString& buf,
|
||||
UErrorCode& status);
|
||||
|
||||
/**
|
||||
* Glue method to get around access restrictions in C++.
|
||||
|
|
Loading…
Add table
Reference in a new issue