001 /* Copyright (c) 2002 Graz University of Technology. All rights reserved.
002 *
003 * Redistribution and use in source and binary forms, with or without
004 * modification, are permitted provided that the following conditions are met:
005 *
006 * 1. Redistributions of source code must retain the above copyright notice,
007 * this list of conditions and the following disclaimer.
008 *
009 * 2. Redistributions in binary form must reproduce the above copyright notice,
010 * this list of conditions and the following disclaimer in the documentation
011 * and/or other materials provided with the distribution.
012 *
013 * 3. The end-user documentation included with the redistribution, if any, must
014 * include the following acknowledgment:
015 *
016 * "This product includes software developed by IAIK of Graz University of
017 * Technology."
018 *
019 * Alternately, this acknowledgment may appear in the software itself, if
020 * and wherever such third-party acknowledgments normally appear.
021 *
022 * 4. The names "Graz University of Technology" and "IAIK of Graz University of
023 * Technology" must not be used to endorse or promote products derived from
024 * this software without prior written permission.
025 *
026 * 5. Products derived from this software may not be called
027 * "IAIK PKCS Wrapper", nor may "IAIK" appear in their name, without prior
028 * written permission of Graz University of Technology.
029 *
030 * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESSED OR IMPLIED
031 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
032 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
033 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE LICENSOR BE
034 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
035 * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
036 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
037 * OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
038 * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
039 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
040 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
041 * POSSIBILITY OF SUCH DAMAGE.
042 */
043
044 package demo.pkcs.pkcs11;
045
046 import java.io.FileInputStream;
047 import java.io.IOException;
048 import java.io.InputStream;
049 import java.math.BigInteger;
050 import java.security.GeneralSecurityException;
051 import java.security.Security;
052 import java.security.Signature;
053 import java.security.cert.CertificateFactory;
054 import java.security.cert.X509Certificate;
055
056 import javax.crypto.Cipher;
057
058 import iaik.security.provider.IAIK;
059 import iaik.utils.Util;
060
061
062
063 public class VerifySignature {
064
065 protected X509Certificate certificate_;
066
067 protected Signature verifyEngine_;
068
069 public VerifySignature(X509Certificate certificate, String algorithm)
070 throws GeneralSecurityException
071 {
072 certificate_ = certificate;
073 // verifyEngine_ = Signature.getInstance(algorithm, "IAIK");
074 verifyEngine_ = Signature.getInstance(algorithm);
075 verifyEngine_.initVerify(certificate.getPublicKey());
076 }
077
078 public boolean verify(InputStream data, byte[] signature)
079 throws IOException, GeneralSecurityException
080 {
081 byte[] buffer = new byte[1024];
082 int bytesRead;
083
084 while ((bytesRead = data.read(buffer, 0, buffer.length)) >= 0) {
085 verifyEngine_.update(buffer, 0, bytesRead);
086 }
087
088 return verifyEngine_.verify(signature) ;
089 }
090
091 public static void main(String[] args) {
092 if (args.length != 4) {
093 printUsage();
094 System.exit(1);
095 }
096
097 try {
098 FileInputStream dataInput = new FileInputStream(args[0]);
099 byte[] signature = Util.readStream(new FileInputStream(args[1]));
100 FileInputStream certificateInput = new FileInputStream(args[2]);
101 Security.addProvider(new IAIK());
102 //CertificateFactory certificateFactory = CertificateFactory.getInstance("X.509", "IAIK");
103 CertificateFactory certificateFactory = CertificateFactory.getInstance("X.509");
104 X509Certificate certificate = (X509Certificate) certificateFactory.generateCertificate(certificateInput);
105
106 VerifySignature verifier = new VerifySignature(certificate, args[3]);
107
108 if (verifier.verify(dataInput, signature)) {
109 System.out.println("Verified signature successfully.");
110 } else {
111 System.out.println("Signature is INVALID.");
112 Cipher rsa = Cipher.getInstance("RSA/ECB/NoPadding");
113 rsa.init(Cipher.DECRYPT_MODE, certificate.getPublicKey());
114 byte[] signedBlock = rsa.doFinal(signature);
115 System.out.println("Decrypted signature value is (hex):");
116 System.out.println(new BigInteger(1, signedBlock).toString(16));
117 }
118
119 } catch (Throwable thr) {
120 thr.printStackTrace();
121 }
122 }
123
124 public static void printUsage() {
125 System.out.println("Usage: VerifySignature <data file> <signature file> <X.509 certificate file> <algorithm>");
126 System.out.println(" e.g.: VerifySignature data.dat signature.bin signerCertificate.der SHA1withRSA");
127 }
128
129
130 }