任何人都可以告诉我如何为我上传的文件实现paillier算法这是我的代码..
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.math.*;
import java.util.*;
import java.lang.*;
public class Paillier {
//*******************************paillier encryption******************************
private BigInteger p, q, lambda;
/**
* n = p*q, where p and q are two large primes.
*/
public BigInteger n;
/**
* nsquare = n*n
*/
public BigInteger nsquare;
/**
* a random integer in Z*_{n^2} where gcd (L(g^lambda mod n^2), n) = 1.
*/
private BigInteger g;
/**
* number of bits of modulus
*/
private int bitLength;
/**
* Constructs an instance of the Paillier cryptosystem.
* @param bitLengthVal number of bits of modulus
* @param certainty The probability that the new BigInteger represents a prime number will exceed (1 - 2^(-certainty)). The execution time of this constructor is proportional to the value of this parameter.
*/
public Paillier(int bitLengthVal, int certainty) {
KeyGeneration(bitLengthVal, certainty);
}
/**
* Constructs an instance of the Paillier cryptosystem with 1024 or 512 bits of modulus and at least 1-2^(-64) certainty of primes generation.
*/
public Paillier() {
KeyGeneration(512, 64);
}
/**
* Sets up the public key and private key.
* @param bitLengthVal number of bits of modulus.
* @param certainty The probability that the new BigInteger represents a prime number will exceed (1 - 2^(-certainty)). The execution time of this constructor is proportional to the value of this parameter.
*/
public void KeyGeneration(int bitLengthVal, int certainty) {
bitLength = bitLengthVal;
/*Constructs two randomly generated positive BigIntegers that are probably prime, with the specified bitLength and certainty.*/
p = new BigInteger(bitLength / 2, certainty, new Random());
q = new BigInteger(bitLength / 2, certainty, new Random());
n = p.multiply(q);
nsquare = n.multiply(n);
g = new BigInteger("2");
lambda = p.subtract(BigInteger.ONE).multiply(q.subtract(BigInteger.ONE)).divide(
p.subtract(BigInteger.ONE).gcd(q.subtract(BigInteger.ONE)));
/* check whether g is good.*/
if (g.modPow(lambda, nsquare).subtract(BigInteger.ONE).divide(n).gcd(n).intValue() != 1) {
System.out.println("g is not good. Choose g again.");
System.exit(1);
}
}
/**
* Encrypts plaintext m. ciphertext c = g^m * r^n mod n^2. This function explicitly requires random input r to help with encryption.
* @param m plaintext as a BigInteger
* @param r random plaintext to help with encryption
* @return ciphertext as a BigInteger
*/
public BigInteger Encryption(BigInteger m, BigInteger r) {
return g.modPow(m, nsquare).multiply(r.modPow(n, nsquare)).mod(nsquare);
}
/**
* Encrypts plaintext m. ciphertext c = g^m * r^n mod n^2. This function automatically generates random input r (to help with encryption).
* @param m plaintext as a BigInteger
* @return ciphertext as a BigInteger
*/
public BigInteger Encryption(BigInteger m) {
BigInteger r = new BigInteger(bitLength, new Random());
return g.modPow(m, nsquare).multiply(r.modPow(n, nsquare)).mod(nsquare);
}
/**
* Decrypts ciphertext c. plaintext m = L(c^lambda mod n^2) * u mod n, where u = (L(g^lambda mod n^2))^(-1) mod n.
* @param c ciphertext as a BigInteger
* @return plaintext as a BigInteger
*/
public BigInteger Decryption(BigInteger c) {
BigInteger u = g.modPow(lambda, nsquare).subtract(BigInteger.ONE).divide(n).modInverse(n);
return c.modPow(lambda, nsquare).subtract(BigInteger.ONE).divide(n).multiply(u).mod(n);
}
//********************************file part main************************
public static void main(String[] args) {
//******************paillier***************
Paillier paillier = new Paillier();
//********************file part**************
File file = new File(args[0]);//path of file
if (!file.exists()) {
System.out.println(args[0] + " does not exist.");
return;
}
if (!(file.isFile() && file.canRead())) {
System.out.println(file.getName() + " cannot be read from.");
return;
}
try {
FileInputStream fis = new FileInputStream(file);
char msg;
String m1;
while (fis.available() > 0) {
msg = (char) fis.read();
// System.out.print(msg);
m1=Character.toString(msg);
//System.out.print(m1);//plain text
BigInteger bi = new BigInteger(m1.getBytes());
//System.out.print(bi);//bit converted text
//System.out.print(new String(bi.toByteArray()));//regained plain text
/* instantiating two plaintext msgs*/
BigInteger m = new BigInteger("bi");
BigInteger m2 = new BigInteger("1");
/* encryption*/
BigInteger em1 = paillier.Encryption(m);
BigInteger em2 = paillier.Encryption(m2);
System.out.println(paillier.Decryption(em1).toString());
//System.out.println(paillier.Decryption(em2).toString());
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
在这里,我想让我的文件字符大写和加密,但我不知道这样做请解决这个问题我发送plaint文本说"感谢你"在文件sample.txt中使用命令行参数
答案 0 :(得分:2)
我认为你可能会欣赏我的一个旧项目的三段代码:
这些方法是类PaillierPrivateKey
的成员。
请注意,我没有使用$ \ lambda = \ varphi(n)$,而是这个数字d
的倍数,与1 modulo n
一致。这样,如果我将密文$ m(n + 1)r ^ n $提升到幂d
,我们只剩下$ m(n + 1)$。
此外,此方法返回私钥。要从此元组获取公钥,只需使用n
。
/**
* generate
* generate a private key for the Paillier cryptosystem where the
* primes have bitLength bits
* @param bitLength
* @return
*/
public static PaillierPrivateKey generate(int bitLength)
{
BigInteger p = new SafePrime(bitLength);
BigInteger q = new SafePrime(bitLength);
return generate( p, q );
}
public static PaillierPrivateKey generate(BigInteger p, BigInteger q)
{
BigInteger n = p.multiply(q);
BigInteger m = p.subtract(BigInteger.ONE).divide(BigInteger.valueOf(2))
.multiply( q.subtract(BigInteger.ONE).divide(BigInteger.valueOf(2)));
BigInteger d = m.modInverse(n).multiply(m).mod(n.multiply(n));
return new PaillierPrivateKey( n, d );
}
这些方法是类PaillierPublicKey
的成员。函数getProduct()
返回$ n $,而getModulus()
返回$ n ^ 2 $,getGenerator()
返回$ n + 1 $。类构造函数RandomInvertibleBigInteger
获取模数(即$ n ^ 2 $)并返回$ {1,...,n ^ 2} $范围内的随机整数,并确保它在乘法模数下是可逆的$ N ^ 2 $。 (对于实际$ n $千位,随机选择很好;对于小玩具示例,你想过滤掉零除数。)
@Override
public BigInteger encrypt(BigInteger plaintext)
{
BigInteger rand = new RandomInvertibleBigInteger( getProduct() );
return encrypt(plaintext, rand);
}
public BigInteger encrypt(BigInteger plaintext, BigInteger rand)
{
BigInteger gm = getGenerator().modPow(plaintext,getModulus());
BigInteger rns = rand.modPow(getProduct(), getModulus());
BigInteger gmrns = gm.multiply(rns);
BigInteger ciphertext = gmrns.mod(getModulus());
return ciphertext;
}
此方法也是PaillierPrivateKey
的成员。同样,getModulus()
返回$ n ^ 2 $而getProduct()
返回$ n $。函数getPrivateExponent()
返回上面描述的漂亮整数d
。
public BigInteger decrypt( BigInteger ciphertext )
{
return ciphertext.modPow( getPrivateExponent(),
getModulus() )
.subtract(BigInteger.ONE)
.divide(getProduct());
}