diff options
Diffstat (limited to 'libraries/spongycastle/core/src/main/java/org/spongycastle/pqc/math/linearalgebra/BigEndianConversions.java')
-rw-r--r-- | libraries/spongycastle/core/src/main/java/org/spongycastle/pqc/math/linearalgebra/BigEndianConversions.java | 306 |
1 files changed, 306 insertions, 0 deletions
diff --git a/libraries/spongycastle/core/src/main/java/org/spongycastle/pqc/math/linearalgebra/BigEndianConversions.java b/libraries/spongycastle/core/src/main/java/org/spongycastle/pqc/math/linearalgebra/BigEndianConversions.java new file mode 100644 index 000000000..4ed7f1c91 --- /dev/null +++ b/libraries/spongycastle/core/src/main/java/org/spongycastle/pqc/math/linearalgebra/BigEndianConversions.java @@ -0,0 +1,306 @@ +package org.spongycastle.pqc.math.linearalgebra; + + +/** + * This is a utility class containing data type conversions using big-endian + * byte order. + * + * @see LittleEndianConversions + */ +public final class BigEndianConversions +{ + + /** + * Default constructor (private). + */ + private BigEndianConversions() + { + // empty + } + + /** + * Convert an integer to an octet string of length 4 according to IEEE 1363, + * Section 5.5.3. + * + * @param x the integer to convert + * @return the converted integer + */ + public static byte[] I2OSP(int x) + { + byte[] result = new byte[4]; + result[0] = (byte)(x >>> 24); + result[1] = (byte)(x >>> 16); + result[2] = (byte)(x >>> 8); + result[3] = (byte)x; + return result; + } + + /** + * Convert an integer to an octet string according to IEEE 1363, Section + * 5.5.3. Length checking is performed. + * + * @param x the integer to convert + * @param oLen the desired length of the octet string + * @return an octet string of length <tt>oLen</tt> representing the + * integer <tt>x</tt>, or <tt>null</tt> if the integer is + * negative + * @throws ArithmeticException if <tt>x</tt> can't be encoded into <tt>oLen</tt> + * octets. + */ + public static byte[] I2OSP(int x, int oLen) + throws ArithmeticException + { + if (x < 0) + { + return null; + } + int octL = IntegerFunctions.ceilLog256(x); + if (octL > oLen) + { + throw new ArithmeticException( + "Cannot encode given integer into specified number of octets."); + } + byte[] result = new byte[oLen]; + for (int i = oLen - 1; i >= oLen - octL; i--) + { + result[i] = (byte)(x >>> (8 * (oLen - 1 - i))); + } + return result; + } + + /** + * Convert an integer to an octet string of length 4 according to IEEE 1363, + * Section 5.5.3. + * + * @param input the integer to convert + * @param output byte array holding the output + * @param outOff offset in output array where the result is stored + */ + public static void I2OSP(int input, byte[] output, int outOff) + { + output[outOff++] = (byte)(input >>> 24); + output[outOff++] = (byte)(input >>> 16); + output[outOff++] = (byte)(input >>> 8); + output[outOff] = (byte)input; + } + + /** + * Convert an integer to an octet string of length 8 according to IEEE 1363, + * Section 5.5.3. + * + * @param input the integer to convert + * @return the converted integer + */ + public static byte[] I2OSP(long input) + { + byte[] output = new byte[8]; + output[0] = (byte)(input >>> 56); + output[1] = (byte)(input >>> 48); + output[2] = (byte)(input >>> 40); + output[3] = (byte)(input >>> 32); + output[4] = (byte)(input >>> 24); + output[5] = (byte)(input >>> 16); + output[6] = (byte)(input >>> 8); + output[7] = (byte)input; + return output; + } + + /** + * Convert an integer to an octet string of length 8 according to IEEE 1363, + * Section 5.5.3. + * + * @param input the integer to convert + * @param output byte array holding the output + * @param outOff offset in output array where the result is stored + */ + public static void I2OSP(long input, byte[] output, int outOff) + { + output[outOff++] = (byte)(input >>> 56); + output[outOff++] = (byte)(input >>> 48); + output[outOff++] = (byte)(input >>> 40); + output[outOff++] = (byte)(input >>> 32); + output[outOff++] = (byte)(input >>> 24); + output[outOff++] = (byte)(input >>> 16); + output[outOff++] = (byte)(input >>> 8); + output[outOff] = (byte)input; + } + + /** + * Convert an integer to an octet string of the specified length according + * to IEEE 1363, Section 5.5.3. No length checking is performed (i.e., if + * the integer cannot be encoded into <tt>length</tt> octets, it is + * truncated). + * + * @param input the integer to convert + * @param output byte array holding the output + * @param outOff offset in output array where the result is stored + * @param length the length of the encoding + */ + public static void I2OSP(int input, byte[] output, int outOff, int length) + { + for (int i = length - 1; i >= 0; i--) + { + output[outOff + i] = (byte)(input >>> (8 * (length - 1 - i))); + } + } + + /** + * Convert an octet string to an integer according to IEEE 1363, Section + * 5.5.3. + * + * @param input the byte array holding the octet string + * @return an integer representing the octet string <tt>input</tt>, or + * <tt>0</tt> if the represented integer is negative or too large + * or the byte array is empty + * @throws ArithmeticException if the length of the given octet string is larger than 4. + */ + public static int OS2IP(byte[] input) + { + if (input.length > 4) + { + throw new ArithmeticException("invalid input length"); + } + if (input.length == 0) + { + return 0; + } + int result = 0; + for (int j = 0; j < input.length; j++) + { + result |= (input[j] & 0xff) << (8 * (input.length - 1 - j)); + } + return result; + } + + /** + * Convert a byte array of length 4 beginning at <tt>offset</tt> into an + * integer. + * + * @param input the byte array + * @param inOff the offset into the byte array + * @return the resulting integer + */ + public static int OS2IP(byte[] input, int inOff) + { + int result = (input[inOff++] & 0xff) << 24; + result |= (input[inOff++] & 0xff) << 16; + result |= (input[inOff++] & 0xff) << 8; + result |= input[inOff] & 0xff; + return result; + } + + /** + * Convert an octet string to an integer according to IEEE 1363, Section + * 5.5.3. + * + * @param input the byte array holding the octet string + * @param inOff the offset in the input byte array where the octet string + * starts + * @param inLen the length of the encoded integer + * @return an integer representing the octet string <tt>bytes</tt>, or + * <tt>0</tt> if the represented integer is negative or too large + * or the byte array is empty + */ + public static int OS2IP(byte[] input, int inOff, int inLen) + { + if ((input.length == 0) || input.length < inOff + inLen - 1) + { + return 0; + } + int result = 0; + for (int j = 0; j < inLen; j++) + { + result |= (input[inOff + j] & 0xff) << (8 * (inLen - j - 1)); + } + return result; + } + + /** + * Convert a byte array of length 8 beginning at <tt>inOff</tt> into a + * long integer. + * + * @param input the byte array + * @param inOff the offset into the byte array + * @return the resulting long integer + */ + public static long OS2LIP(byte[] input, int inOff) + { + long result = ((long)input[inOff++] & 0xff) << 56; + result |= ((long)input[inOff++] & 0xff) << 48; + result |= ((long)input[inOff++] & 0xff) << 40; + result |= ((long)input[inOff++] & 0xff) << 32; + result |= ((long)input[inOff++] & 0xff) << 24; + result |= (input[inOff++] & 0xff) << 16; + result |= (input[inOff++] & 0xff) << 8; + result |= input[inOff] & 0xff; + return result; + } + + /** + * Convert an int array into a byte array. + * + * @param input the int array + * @return the converted array + */ + public static byte[] toByteArray(final int[] input) + { + byte[] result = new byte[input.length << 2]; + for (int i = 0; i < input.length; i++) + { + I2OSP(input[i], result, i << 2); + } + return result; + } + + /** + * Convert an int array into a byte array of the specified length. No length + * checking is performed (i.e., if the last integer cannot be encoded into + * <tt>length % 4</tt> octets, it is truncated). + * + * @param input the int array + * @param length the length of the converted array + * @return the converted array + */ + public static byte[] toByteArray(final int[] input, int length) + { + final int intLen = input.length; + byte[] result = new byte[length]; + int index = 0; + for (int i = 0; i <= intLen - 2; i++, index += 4) + { + I2OSP(input[i], result, index); + } + I2OSP(input[intLen - 1], result, index, length - index); + return result; + } + + /** + * Convert a byte array into an int array. + * + * @param input the byte array + * @return the converted array + */ + public static int[] toIntArray(byte[] input) + { + final int intLen = (input.length + 3) / 4; + final int lastLen = input.length & 0x03; + int[] result = new int[intLen]; + + int index = 0; + for (int i = 0; i <= intLen - 2; i++, index += 4) + { + result[i] = OS2IP(input, index); + } + if (lastLen != 0) + { + result[intLen - 1] = OS2IP(input, index, lastLen); + } + else + { + result[intLen - 1] = OS2IP(input, index); + } + + return result; + } + +} |