/** * Calculates the checksum for the given data. * * @param charset the charset used in encoding the data * @param data the data to calculate the checksum on * @param isEntireMessage specifies whether the data is an entire message; if true, and it ends * with a checksum field, that checksum field is excluded from the current checksum * calculation * @return the calculated checksum */ public static int checksum(Charset charset, String data, boolean isEntireMessage) { int sum = 0; if (CharsetSupport.isStringEquivalent(charset)) { // optimization - skip encoding int end = isEntireMessage ? data.lastIndexOf("\00110=") : -1; int len = end > -1 ? end + 1 : data.length(); for (int i = 0; i < len; i++) { sum += data.charAt(i); } } else { byte[] bytes = data.getBytes(charset); int len = bytes.length; if (isEntireMessage && bytes[len - 8] == '\001' && bytes[len - 7] == '1' && bytes[len - 6] == '0' && bytes[len - 5] == '=') len = len - 7; for (int i = 0; i < len; i++) { sum += (bytes[i] & 0xFF); } } return sum & 0xFF; // better than sum % 256 since it avoids overflow issues }
/** * Calculates the length of the byte representation of the given string in the given charset. * * @param charset the charset used in encoding the data * @param data the data to calculate the length on * @return the calculated length */ public static int length(Charset charset, String data) { return CharsetSupport.isStringEquivalent(charset) ? data.length() : data.getBytes(charset).length; }