return 0;
}
throw new IllegalArgumentException("Illegal maxLength ("+maxLength+"), has to be positive number, and offset+maxLength can not exceed"+resultBuffer.length);
}
final CharArrayBase64Decoder dec = _base64Decoder();
int type = _currToken;
// First things first: must be acceptable start state:
if (((1 << type) & MASK_TYPED_ACCESS_BINARY) == 0) {
if (type == END_ELEMENT) {
// Minor complication: may have unflushed stuff (non-padded versions)
if (!dec.hasData()) {
return -1;
}
} else {
throw new IllegalStateException(ErrorConsts.ERR_STATE_NOT_STELEM_OR_TEXT);
}
} else if (type == START_ELEMENT) { // just starting (START_ELEMENT)?
if (_scanner.isEmptyTag()) {
// might be possible to optimize, but for now this'll do:
next();
return -1;
}
// Otherwise let's just find the first text segment
while (true) {
type = next();
if (type == END_ELEMENT) { // Simple, no textual content
return -1;
}
if (type == COMMENT || type == PROCESSING_INSTRUCTION) {
continue;
}
if (type == CHARACTERS || type == CDATA) {
break;
}
// otherwise just not legal (how about SPACE, unexpanded entities?)
throw _constructUnexpectedInTyped(type);
}
_scanner.resetForDecoding(v, dec, true); // true -> first segment
}
int totalCount = 0;
main_loop:
while (true) {
// Ok, decode:
int count;
try {
count = dec.decode(resultBuffer, offset, maxLength);
} catch (IllegalArgumentException iae) {
// !!! 26-Sep-2008, tatus: should try to figure out which char (etc) triggered problem to pass with typed exception
throw _constructTypeException(iae.getMessage(), "");
}
offset += count;
totalCount += count;
maxLength -= count;
/* And if we filled the buffer we are done. Or, an edge
* case: reached END_ELEMENT (for non-padded variant)
*/
if (maxLength < 1 || _currToken == END_ELEMENT) {
break;
}
// Otherwise need to advance to the next event
while (true) {
type = next();
if (type == COMMENT || type == PROCESSING_INSTRUCTION
|| type == SPACE) { // space is ignorable too
continue;
}
if (type == END_ELEMENT) {
/* Just need to verify we don't have partial stuff
* (missing one to three characters of a full quartet
* that encodes 1 - 3 bytes). Also: non-padding
* variants can be in incomplete state, from which
* data may need to be flushed...
*/
int left = dec.endOfContent();
if (left < 0) { // incomplete, error
throw _constructTypeException("Incomplete base64 triplet at the end of decoded content", "");
} else if (left > 0) { // 1 or 2 more bytes of data, loop some more
continue main_loop;
}