SHA1withDSA_SignatureImplpublic class SHA1withDSA_SignatureImpl extends Signature
Fields Summary |
---|
private MessageDigest | msgDigest | private DSAKey | dsaKey |
Constructors Summary |
---|
public SHA1withDSA_SignatureImpl()The solo constructor.
super("SHA1withDSA"); //$NON-NLS-1$
msgDigest = MessageDigest.getInstance("SHA1"); //$NON-NLS-1$
|
Methods Summary |
---|
private boolean | checkSignature(byte[] sigBytes, int offset, int length)
// names of below BigIntegers are the same as they are defined in DSA standard
BigInteger r, s, w;
BigInteger u1, u2, v;
// parameters and public key
BigInteger p, q, g, y;
DSAParams params;
int n1, n2;
byte bytes[];
byte digest[];
// checking up on signature's ASN1
try {
byte dummy;
n1 = sigBytes[offset + 3];
n2 = sigBytes[offset + n1 + 5];
if (sigBytes[offset + 0] != 0x30 || sigBytes[offset + 2] != 2
|| sigBytes[offset + n1 + 4] != 2
|| sigBytes[offset + 1] != (n1 + n2 + 4) || n1 > 21
|| n2 > 21
|| (length != 0 && (sigBytes[offset + 1] + 2) > length)) {
throw new SignatureException(Messages.getString("security.16F")); //$NON-NLS-1$
}
dummy = sigBytes[5 + n1 + n2]; // to check length of sigBytes
} catch (ArrayIndexOutOfBoundsException e) {
throw new SignatureException(Messages.getString("security.170")); //$NON-NLS-1$
}
digest = msgDigest.digest();
bytes = new byte[n1];
System.arraycopy(sigBytes, offset + 4, bytes, 0, n1);
r = new BigInteger(bytes);
bytes = new byte[n2];
System.arraycopy(sigBytes, offset + 6 + n1, bytes, 0, n2);
s = new BigInteger(bytes);
params = dsaKey.getParams();
p = params.getP();
q = params.getQ();
g = params.getG();
y = ((DSAPublicKey) dsaKey).getY();
// forming signature according algorithm described in chapter 6 of DSA standard
if (r.signum() != 1 || r.compareTo(q) != -1 || s.signum() != 1
|| s.compareTo(q) != -1) {
return false;
}
w = s.modInverse(q);
u1 = (new BigInteger(1, digest)).multiply(w).mod(q);
u2 = r.multiply(w).mod(q);
v = g.modPow(u1, p).multiply(y.modPow(u2, p)).mod(p).mod(q);
if (v.compareTo(r) != 0) {
return false;
}
return true;
| protected java.lang.Object | engineGetParameter(java.lang.String param)Deprecated method.
if (param == null) {
throw new NullPointerException(Messages.getString("security.01")); //$NON-NLS-1$
}
return null;
| protected void | engineInitSign(java.security.PrivateKey privateKey)Initializes this signature object with PrivateKey object
passed as argument to the method.
DSAParams params;
// parameters and private key
BigInteger p, q, g, x;
int n;
if (privateKey == null || !(privateKey instanceof DSAPrivateKey)) {
throw new InvalidKeyException(
Messages.getString("security.168")); //$NON-NLS-1$
}
params = ((DSAPrivateKey) privateKey).getParams();
p = params.getP();
q = params.getQ();
g = params.getG();
x = ((DSAPrivateKey) privateKey).getX();
// checks described in DSA standard
n = p.bitLength();
if (p.compareTo(BigInteger.valueOf(1)) != 1 || n < 512 || n > 1024
|| (n & 077) != 0) {
throw new InvalidKeyException(Messages.getString("security.169")); //$NON-NLS-1$
}
if (q.signum() != 1 && q.bitLength() != 160) {
throw new InvalidKeyException(Messages.getString("security.16A")); //$NON-NLS-1$
}
if (x.signum() != 1 || x.compareTo(q) != -1) {
throw new InvalidKeyException(Messages.getString("security.16B")); //$NON-NLS-1$
}
dsaKey = (DSAKey) privateKey;
msgDigest.reset();
| protected void | engineInitVerify(java.security.PublicKey publicKey)Initializes this signature object with PublicKey object
passed as argument to the method.
// parameters and public key
BigInteger p, q, g, y;
int n1;
if (publicKey == null || !(publicKey instanceof DSAPublicKey)) {
throw new InvalidKeyException(
Messages.getString("security.16C")); //$NON-NLS-1$
}
DSAParams params = ((DSAPublicKey) publicKey).getParams();
p = params.getP();
q = params.getQ();
g = params.getG();
y = ((DSAPublicKey) publicKey).getY();
// checks described in DSA standard
n1 = p.bitLength();
if (p.compareTo(BigInteger.valueOf(1)) != 1 || n1 < 512 || n1 > 1024
|| (n1 & 077) != 0) {
throw new InvalidKeyException(Messages.getString("security.169")); //$NON-NLS-1$
}
if (q.signum() != 1 || q.bitLength() != 160) {
throw new InvalidKeyException(Messages.getString("security.16A")); //$NON-NLS-1$
}
if (y.signum() != 1) {
throw new InvalidKeyException(Messages.getString("security.16D")); //$NON-NLS-1$
}
dsaKey = (DSAKey) publicKey;
msgDigest.reset();
| protected void | engineSetParameter(java.lang.String param, java.lang.Object value)
if (param == null) {
throw new NullPointerException(Messages.getString("security.83", "param")); //$NON-NLS-1$ //$NON-NLS-2$
}
throw new InvalidParameterException(Messages.getString("security.16E")); //$NON-NLS-1$
| protected byte[] | engineSign()Returns signature bytes as byte array containing
ASN1 representation for two BigInteger objects
which is SEQUENCE of two INTEGERS.
Length of sequence varies from less than 46 to 48.
Resets object to the state it was in
when previous call to either "initSign" method was called.
// names of below BigIntegers are the same as they are defined in DSA standard
BigInteger r = null;
BigInteger s = null;
BigInteger k = null;
// parameters and private key
BigInteger p, q, g, x;
// BigInteger for message digest
BigInteger digestBI;
// various byte array being used in computing signature
byte randomBytes[];
byte digest[];
byte rBytes[], sBytes[], signature[];
int n, n1, n2;
DSAParams params;
if (appRandom == null) {
appRandom = new SecureRandom();
}
params = dsaKey.getParams();
p = params.getP();
q = params.getQ();
g = params.getG();
x = ((DSAPrivateKey) dsaKey).getX();
// forming signature according algorithm described in chapter 5 of DSA standard
digestBI = new BigInteger(1, msgDigest.digest());
randomBytes = new byte[20];
for (;;) {
appRandom.nextBytes(randomBytes);
k = new BigInteger(1, randomBytes);
if (k.compareTo(q) != -1) {
continue;
}
r = g.modPow(k, p).mod(q);
if (r.signum() == 0) {
continue;
}
s = k.modInverse(q).multiply(digestBI.add(x.multiply(r)).mod(q))
.mod(q);
if (s.signum() != 0) {
break;
}
}
// forming signature's ASN1 representation which is SEQUENCE of two INTEGERs
//
rBytes = r.toByteArray();
n1 = rBytes.length;
if ((rBytes[0] & 0x80) != 0) {
n1++;
}
sBytes = s.toByteArray();
n2 = sBytes.length;
if ((sBytes[0] & 0x80) != 0) {
n2++;
}
signature = new byte[6 + n1 + n2]; // 48 is max. possible length of signature
signature[0] = (byte) 0x30; // ASN1 SEQUENCE tag
signature[1] = (byte) (4 + n1 + n2); // total length of two INTEGERs
signature[2] = (byte) 0x02; // ASN1 INTEGER tag
signature[3] = (byte) n1; // length of r
signature[4 + n1] = (byte) 0x02; // ASN1 INTEGER tag
signature[5 + n1] = (byte) n2; // length of s
if (n1 == rBytes.length) {
n = 4;
} else {
n = 5;
}
System.arraycopy(rBytes, 0, signature, n, rBytes.length);
if (n2 == sBytes.length) {
n = 6 + n1;
} else {
n = 7 + n1;
}
System.arraycopy(sBytes, 0, signature, n, sBytes.length);
return signature;
| protected void | engineUpdate(byte b)Updates data to sign or to verify.
msgDigest.update(b);
| protected void | engineUpdate(byte[] b, int off, int len)Updates data to sign or to verify.
msgDigest.update(b, off, len);
| protected boolean | engineVerify(byte[] sigBytes)Verifies the signature bytes.
if (sigBytes == null) {
throw new NullPointerException(Messages.getString("security.83", "sigBytes")); //$NON-NLS-1$ //$NON-NLS-2$
}
return checkSignature(sigBytes, 0, 0);
| protected boolean | engineVerify(byte[] sigBytes, int offset, int length)Verifies the signature bytes.
return checkSignature(sigBytes, offset, length);
|
|