/******************************************************************************* * Copyright (C) 2013 JMaNGOS <http://jmangos.org/> * * This program is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 2 of the License, or (at your * option) any later version. * * This program is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for * more details. * * You should have received a copy of the GNU General Public License along * with this program. If not, see <http://www.gnu.org/licenses/>. ******************************************************************************/ package org.jmangos.commons.utils; import java.math.BigInteger; import java.security.SecureRandom; /** * The Class BigNumber. */ public class BigNumber { /** * Instantiates a new big number. */ public BigNumber() { this.bigInteger = BigInteger.ZERO; } /** * Instantiates a new big number. * * @param bigInteger * the big integer */ public BigNumber(final BigInteger bigInteger) { this.bigInteger = bigInteger.abs(); } /** * Instantiates a new big number. * * @param str * the str */ public BigNumber(final String str) { this.bigInteger = new BigInteger(str, 16); } /** * Instantiates a new big number. * * @param array * the array */ public BigNumber(byte[] array) { // Add the first byte indicates the sign of the BigInteger if (array[0] < 0) { final byte[] tmp = new byte[array.length + 1]; System.arraycopy(array, 0, tmp, 1, array.length); array = tmp; } this.bigInteger = new BigInteger(array); } /** * Adds the. * * @param val * the val * @return the big number */ public BigNumber add(final BigNumber val) { return new BigNumber(this.bigInteger.add(val.getBigInteger())); } /** * Multiply. * * @param val * the val * @return the big number */ public BigNumber multiply(final BigNumber val) { return new BigNumber(this.bigInteger.multiply(val.getBigInteger())); } /** * Sets the hex str. * * @param str * the new hex str */ public void setHexStr(final String str) { this.bigInteger = new BigInteger(str, 16); } /** * Sets the rand. * * @param numBytes * the new rand */ public void setRand(final int numBytes) { final SecureRandom random = new SecureRandom(); final byte[] array = random.generateSeed(numBytes); this.bigInteger = new BigInteger(1, array); } /** * Sets the binary. * * @param array * the new binary */ public void setBinary(byte[] array) { // Reverse array final int length = array.length; for (int i = 0; i < (length / 2); i++) { final byte j = array[i]; array[i] = array[length - 1 - i]; array[length - 1 - i] = j; } // Add the first byte indicates the sign of the BigInteger if (array[0] < 0) { final byte[] tmp = new byte[array.length + 1]; System.arraycopy(array, 0, tmp, 1, array.length); array = tmp; } this.bigInteger = new BigInteger(array); } /** * Mod. * * @param m * the m * @return the big number */ public BigNumber mod(final BigNumber m) { return new BigNumber(this.bigInteger.mod(m.getBigInteger())); } /** * Mod pow. * * @param exponent * the exponent * @param m * the m * @return the big number */ public BigNumber modPow(final BigNumber exponent, final BigNumber m) { return new BigNumber(this.bigInteger.modPow(exponent.getBigInteger(), m.getBigInteger())); } /** * As byte array. * * @param minSize * the min size * @return the byte[] */ public byte[] asByteArray(final int minSize) { // Remove the first byte that indicates the sign of a BigInteger byte[] array = this.bigInteger.toByteArray(); if (array[0] == 0) { final byte[] tmp = new byte[array.length - 1]; System.arraycopy(array, 1, tmp, 0, tmp.length); array = tmp; } // Reverse array final int length = array.length; for (int i = 0; i < (length / 2); i++) { final byte j = array[i]; array[i] = array[length - 1 - i]; array[length - 1 - i] = j; } // If we need more bytes than length of BigNumber set the rest to 0 if (minSize > length) { final byte[] newArray = new byte[minSize]; System.arraycopy(array, 0, newArray, 0, length); return newArray; } return array; } /** * As hex str. * * @return the string */ public String asHexStr() { return this.bigInteger.toString(16).toUpperCase(); } /** * Gets the big integer. * * @return the big integer */ public BigInteger getBigInteger() { return this.bigInteger.abs(); } /** The big integer. */ private BigInteger bigInteger; }