2 *******************************************************************************
\r
3 * Copyright (C) 1996-2010, International Business Machines Corporation and *
\r
4 * others. All Rights Reserved. *
\r
5 *******************************************************************************
\r
9 package com.ibm.icu.text;
\r
12 * This class matches UTF-16 and UTF-32, both big- and little-endian. The
\r
13 * BOM will be used if it is present.
\r
15 abstract class CharsetRecog_Unicode extends CharsetRecognizer {
\r
18 * @see com.ibm.icu.text.CharsetRecognizer#getName()
\r
20 abstract String getName();
\r
23 * @see com.ibm.icu.text.CharsetRecognizer#match(com.ibm.icu.text.CharsetDetector)
\r
25 abstract int match(CharsetDetector det);
\r
27 static class CharsetRecog_UTF_16_BE extends CharsetRecog_Unicode
\r
34 int match(CharsetDetector det)
\r
36 byte[] input = det.fRawInput;
\r
38 if (input.length>=2 && ((input[0] & 0xFF) == 0xFE && (input[1] & 0xFF) == 0xFF)) {
\r
42 // TODO: Do some statistics to check for unsigned UTF-16BE
\r
47 static class CharsetRecog_UTF_16_LE extends CharsetRecog_Unicode
\r
54 int match(CharsetDetector det)
\r
56 byte[] input = det.fRawInput;
\r
58 if (input.length >= 2 && ((input[0] & 0xFF) == 0xFF && (input[1] & 0xFF) == 0xFE))
\r
60 // An LE BOM is present.
\r
61 if (input.length>=4 && input[2] == 0x00 && input[3] == 0x00) {
\r
62 // It is probably UTF-32 LE, not UTF-16
\r
68 // TODO: Do some statistics to check for unsigned UTF-16LE
\r
73 static abstract class CharsetRecog_UTF_32 extends CharsetRecog_Unicode
\r
75 abstract int getChar(byte[] input, int index);
\r
77 abstract String getName();
\r
79 int match(CharsetDetector det)
\r
81 byte[] input = det.fRawInput;
\r
82 int limit = (det.fRawLength / 4) * 4;
\r
85 boolean hasBOM = false;
\r
91 if (getChar(input, 0) == 0x0000FEFF) {
\r
95 for(int i = 0; i < limit; i += 4) {
\r
96 int ch = getChar(input, i);
\r
98 if (ch < 0 || ch >= 0x10FFFF || (ch >= 0xD800 && ch <= 0xDFFF)) {
\r
106 // Cook up some sort of confidence score, based on presence of a BOM
\r
107 // and the existence of valid and/or invalid multi-byte sequences.
\r
108 if (hasBOM && numInvalid==0) {
\r
110 } else if (hasBOM && numValid > numInvalid*10) {
\r
112 } else if (numValid > 3 && numInvalid == 0) {
\r
114 } else if (numValid > 0 && numInvalid == 0) {
\r
116 } else if (numValid > numInvalid*10) {
\r
117 // Probably corrupt UTF-32BE data. Valid sequences aren't likely by chance.
\r
125 static class CharsetRecog_UTF_32_BE extends CharsetRecog_UTF_32
\r
127 int getChar(byte[] input, int index)
\r
129 return (input[index + 0] & 0xFF) << 24 | (input[index + 1] & 0xFF) << 16 |
\r
130 (input[index + 2] & 0xFF) << 8 | (input[index + 3] & 0xFF);
\r
140 static class CharsetRecog_UTF_32_LE extends CharsetRecog_UTF_32
\r
142 int getChar(byte[] input, int index)
\r
144 return (input[index + 3] & 0xFF) << 24 | (input[index + 2] & 0xFF) << 16 |
\r
145 (input[index + 1] & 0xFF) << 8 | (input[index + 0] & 0xFF);
\r