Cryptography Reference
In-Depth Information
public class Ciphers {
public static byte[] rabinEncipherWSalt(byte[] msg,BigInteger n,SecureRandom sr)
{
//Compute the plaintext block size-take 4 bytes salt and 4 bytes redundancy
//into account
int blockSize=(n.bitLength()-1)/8;
if (blockSize<12) throw new IllegalArgumentException
(“Block size must be >= 12 bytes”);
byte[][] ba=block(pad(msg,blockSize-8),blockSize-8);
//Begin the enciphering
for (int i=0;i<ba.length;i++) {
ba[i]=addRedundancyAndSalt(ba[i],sr);
ba[i]=getBytes(new BigInteger(1,ba[i]).modPow(BigIntegerMath.TWO,n));
}
//Return to a 1D array. The ciphertext block size is one byte greater than
//plaintext block size.
return unBlock(ba,blockSize+1);
}
public static byte[] rabinDecipherWSalt(byte[] msg,BigInteger p,BigInteger q) {
//Compute inverse of p mod q, and of q mod p
BigInteger n=p.multiply(q);
BigInteger pinv=p.modInverse(q);
BigInteger qinv=q.modInverse(p);
BigInteger pexp=(p.add(BigIntegerMath.ONE)).divide(BigIntegerMath.FOUR);
BigInteger qexp=(q.add(BigIntegerMath.ONE)).divide(BigIntegerMath.FOUR);
//Compute the ciphertext block size
int blockSize=(n.bitLength()-1)/8+1;
byte[][] ba=block(msg,blockSize);
//Begin the deciphering
for (int i=0;i<ba.length;i++) {
//Get the four roots
BigInteger term1=new BigInteger(1,ba[i])
.modPow(pexp,n).multiply(q).multiply(qinv);
BigInteger term2=new BigInteger(1,ba[i]).
modPow(qexp,n).multiply(p).multiply(pinv);
byte[][] msgroot=new byte[4][0];
BigInteger sum=term1.add(term2);
BigInteger difference=term1.subtract(term2);
msgroot[0]=getBytes(BigIntegerMath.lnr(sum,n));
msgroot[1]=getBytes(BigIntegerMath.lnr(sum.negate(),n));
msgroot[2]=getBytes(BigIntegerMath.lnr(difference,n));
msgroot[3]=getBytes(BigIntegerMath.lnr(difference.negate(),n));
boolean[] isCorrectRoot=new boolean[4];
for (int k=0;k<4;k++) {
isCorrectRoot[k]=true;
Search WWH ::




Custom Search