1*288bf522SAndroid Build Coastguard Worker /* 2*288bf522SAndroid Build Coastguard Worker * Copyright (C) 2014 The Android Open Source Project 3*288bf522SAndroid Build Coastguard Worker * 4*288bf522SAndroid Build Coastguard Worker * Licensed under the Apache License, Version 2.0 (the "License"); 5*288bf522SAndroid Build Coastguard Worker * you may not use this file except in compliance with the License. 6*288bf522SAndroid Build Coastguard Worker * You may obtain a copy of the License at 7*288bf522SAndroid Build Coastguard Worker * 8*288bf522SAndroid Build Coastguard Worker * http://www.apache.org/licenses/LICENSE-2.0 9*288bf522SAndroid Build Coastguard Worker * 10*288bf522SAndroid Build Coastguard Worker * Unless required by applicable law or agreed to in writing, software 11*288bf522SAndroid Build Coastguard Worker * distributed under the License is distributed on an "AS IS" BASIS, 12*288bf522SAndroid Build Coastguard Worker * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13*288bf522SAndroid Build Coastguard Worker * See the License for the specific language governing permissions and 14*288bf522SAndroid Build Coastguard Worker * limitations under the License. 15*288bf522SAndroid Build Coastguard Worker */ 16*288bf522SAndroid Build Coastguard Worker 17*288bf522SAndroid Build Coastguard Worker package com.android.verity; 18*288bf522SAndroid Build Coastguard Worker 19*288bf522SAndroid Build Coastguard Worker import java.lang.reflect.Constructor; 20*288bf522SAndroid Build Coastguard Worker import java.io.File; 21*288bf522SAndroid Build Coastguard Worker import java.io.ByteArrayInputStream; 22*288bf522SAndroid Build Coastguard Worker import java.io.Console; 23*288bf522SAndroid Build Coastguard Worker import java.io.FileInputStream; 24*288bf522SAndroid Build Coastguard Worker import java.io.FileOutputStream; 25*288bf522SAndroid Build Coastguard Worker import java.io.InputStreamReader; 26*288bf522SAndroid Build Coastguard Worker import java.io.IOException; 27*288bf522SAndroid Build Coastguard Worker import java.security.GeneralSecurityException; 28*288bf522SAndroid Build Coastguard Worker import java.security.Key; 29*288bf522SAndroid Build Coastguard Worker import java.security.PrivateKey; 30*288bf522SAndroid Build Coastguard Worker import java.security.PublicKey; 31*288bf522SAndroid Build Coastguard Worker import java.security.KeyFactory; 32*288bf522SAndroid Build Coastguard Worker import java.security.Provider; 33*288bf522SAndroid Build Coastguard Worker import java.security.Security; 34*288bf522SAndroid Build Coastguard Worker import java.security.Signature; 35*288bf522SAndroid Build Coastguard Worker import java.security.cert.Certificate; 36*288bf522SAndroid Build Coastguard Worker import java.security.cert.CertificateFactory; 37*288bf522SAndroid Build Coastguard Worker import java.security.cert.X509Certificate; 38*288bf522SAndroid Build Coastguard Worker import java.security.spec.ECPublicKeySpec; 39*288bf522SAndroid Build Coastguard Worker import java.security.spec.ECPrivateKeySpec; 40*288bf522SAndroid Build Coastguard Worker import java.security.spec.X509EncodedKeySpec; 41*288bf522SAndroid Build Coastguard Worker import java.security.spec.PKCS8EncodedKeySpec; 42*288bf522SAndroid Build Coastguard Worker import java.security.spec.InvalidKeySpecException; 43*288bf522SAndroid Build Coastguard Worker import java.util.Arrays; 44*288bf522SAndroid Build Coastguard Worker import java.util.HashMap; 45*288bf522SAndroid Build Coastguard Worker import java.util.Map; 46*288bf522SAndroid Build Coastguard Worker 47*288bf522SAndroid Build Coastguard Worker import javax.crypto.Cipher; 48*288bf522SAndroid Build Coastguard Worker import javax.crypto.EncryptedPrivateKeyInfo; 49*288bf522SAndroid Build Coastguard Worker import javax.crypto.SecretKeyFactory; 50*288bf522SAndroid Build Coastguard Worker import javax.crypto.spec.PBEKeySpec; 51*288bf522SAndroid Build Coastguard Worker 52*288bf522SAndroid Build Coastguard Worker import org.bouncycastle.asn1.ASN1InputStream; 53*288bf522SAndroid Build Coastguard Worker import org.bouncycastle.asn1.ASN1ObjectIdentifier; 54*288bf522SAndroid Build Coastguard Worker import org.bouncycastle.asn1.pkcs.PrivateKeyInfo; 55*288bf522SAndroid Build Coastguard Worker import org.bouncycastle.asn1.pkcs.PKCSObjectIdentifiers; 56*288bf522SAndroid Build Coastguard Worker import org.bouncycastle.asn1.x509.AlgorithmIdentifier; 57*288bf522SAndroid Build Coastguard Worker import org.bouncycastle.asn1.x9.X9ObjectIdentifiers; 58*288bf522SAndroid Build Coastguard Worker import org.bouncycastle.util.encoders.Base64; 59*288bf522SAndroid Build Coastguard Worker 60*288bf522SAndroid Build Coastguard Worker public class Utils { 61*288bf522SAndroid Build Coastguard Worker 62*288bf522SAndroid Build Coastguard Worker private static final Map<String, String> ID_TO_ALG; 63*288bf522SAndroid Build Coastguard Worker private static final Map<String, String> ALG_TO_ID; 64*288bf522SAndroid Build Coastguard Worker 65*288bf522SAndroid Build Coastguard Worker static { 66*288bf522SAndroid Build Coastguard Worker ID_TO_ALG = new HashMap<String, String>(); 67*288bf522SAndroid Build Coastguard Worker ALG_TO_ID = new HashMap<String, String>(); 68*288bf522SAndroid Build Coastguard Worker X9ObjectIdentifiers.ecdsa_with_SHA256.getId()69*288bf522SAndroid Build Coastguard Worker ID_TO_ALG.put(X9ObjectIdentifiers.ecdsa_with_SHA256.getId(), "SHA256withECDSA"); X9ObjectIdentifiers.ecdsa_with_SHA384.getId()70*288bf522SAndroid Build Coastguard Worker ID_TO_ALG.put(X9ObjectIdentifiers.ecdsa_with_SHA384.getId(), "SHA384withECDSA"); X9ObjectIdentifiers.ecdsa_with_SHA512.getId()71*288bf522SAndroid Build Coastguard Worker ID_TO_ALG.put(X9ObjectIdentifiers.ecdsa_with_SHA512.getId(), "SHA512withECDSA"); PKCSObjectIdentifiers.sha1WithRSAEncryption.getId()72*288bf522SAndroid Build Coastguard Worker ID_TO_ALG.put(PKCSObjectIdentifiers.sha1WithRSAEncryption.getId(), "SHA1withRSA"); PKCSObjectIdentifiers.sha256WithRSAEncryption.getId()73*288bf522SAndroid Build Coastguard Worker ID_TO_ALG.put(PKCSObjectIdentifiers.sha256WithRSAEncryption.getId(), "SHA256withRSA"); PKCSObjectIdentifiers.sha512WithRSAEncryption.getId()74*288bf522SAndroid Build Coastguard Worker ID_TO_ALG.put(PKCSObjectIdentifiers.sha512WithRSAEncryption.getId(), "SHA512withRSA"); 75*288bf522SAndroid Build Coastguard Worker 76*288bf522SAndroid Build Coastguard Worker ALG_TO_ID.put("SHA256withECDSA", X9ObjectIdentifiers.ecdsa_with_SHA256.getId()); 77*288bf522SAndroid Build Coastguard Worker ALG_TO_ID.put("SHA384withECDSA", X9ObjectIdentifiers.ecdsa_with_SHA384.getId()); 78*288bf522SAndroid Build Coastguard Worker ALG_TO_ID.put("SHA512withECDSA", X9ObjectIdentifiers.ecdsa_with_SHA512.getId()); 79*288bf522SAndroid Build Coastguard Worker ALG_TO_ID.put("SHA1withRSA", PKCSObjectIdentifiers.sha1WithRSAEncryption.getId()); 80*288bf522SAndroid Build Coastguard Worker ALG_TO_ID.put("SHA256withRSA", PKCSObjectIdentifiers.sha256WithRSAEncryption.getId()); 81*288bf522SAndroid Build Coastguard Worker ALG_TO_ID.put("SHA512withRSA", PKCSObjectIdentifiers.sha512WithRSAEncryption.getId()); 82*288bf522SAndroid Build Coastguard Worker } 83*288bf522SAndroid Build Coastguard Worker loadProviderIfNecessary(String providerClassName)84*288bf522SAndroid Build Coastguard Worker private static void loadProviderIfNecessary(String providerClassName) { 85*288bf522SAndroid Build Coastguard Worker if (providerClassName == null) { 86*288bf522SAndroid Build Coastguard Worker return; 87*288bf522SAndroid Build Coastguard Worker } 88*288bf522SAndroid Build Coastguard Worker 89*288bf522SAndroid Build Coastguard Worker final Class<?> klass; 90*288bf522SAndroid Build Coastguard Worker try { 91*288bf522SAndroid Build Coastguard Worker final ClassLoader sysLoader = ClassLoader.getSystemClassLoader(); 92*288bf522SAndroid Build Coastguard Worker if (sysLoader != null) { 93*288bf522SAndroid Build Coastguard Worker klass = sysLoader.loadClass(providerClassName); 94*288bf522SAndroid Build Coastguard Worker } else { 95*288bf522SAndroid Build Coastguard Worker klass = Class.forName(providerClassName); 96*288bf522SAndroid Build Coastguard Worker } 97*288bf522SAndroid Build Coastguard Worker } catch (ClassNotFoundException e) { 98*288bf522SAndroid Build Coastguard Worker e.printStackTrace(); 99*288bf522SAndroid Build Coastguard Worker System.exit(1); 100*288bf522SAndroid Build Coastguard Worker return; 101*288bf522SAndroid Build Coastguard Worker } 102*288bf522SAndroid Build Coastguard Worker 103*288bf522SAndroid Build Coastguard Worker Constructor<?> constructor = null; 104*288bf522SAndroid Build Coastguard Worker for (Constructor<?> c : klass.getConstructors()) { 105*288bf522SAndroid Build Coastguard Worker if (c.getParameterTypes().length == 0) { 106*288bf522SAndroid Build Coastguard Worker constructor = c; 107*288bf522SAndroid Build Coastguard Worker break; 108*288bf522SAndroid Build Coastguard Worker } 109*288bf522SAndroid Build Coastguard Worker } 110*288bf522SAndroid Build Coastguard Worker if (constructor == null) { 111*288bf522SAndroid Build Coastguard Worker System.err.println("No zero-arg constructor found for " + providerClassName); 112*288bf522SAndroid Build Coastguard Worker System.exit(1); 113*288bf522SAndroid Build Coastguard Worker return; 114*288bf522SAndroid Build Coastguard Worker } 115*288bf522SAndroid Build Coastguard Worker 116*288bf522SAndroid Build Coastguard Worker final Object o; 117*288bf522SAndroid Build Coastguard Worker try { 118*288bf522SAndroid Build Coastguard Worker o = constructor.newInstance(); 119*288bf522SAndroid Build Coastguard Worker } catch (Exception e) { 120*288bf522SAndroid Build Coastguard Worker e.printStackTrace(); 121*288bf522SAndroid Build Coastguard Worker System.exit(1); 122*288bf522SAndroid Build Coastguard Worker return; 123*288bf522SAndroid Build Coastguard Worker } 124*288bf522SAndroid Build Coastguard Worker if (!(o instanceof Provider)) { 125*288bf522SAndroid Build Coastguard Worker System.err.println("Not a Provider class: " + providerClassName); 126*288bf522SAndroid Build Coastguard Worker System.exit(1); 127*288bf522SAndroid Build Coastguard Worker } 128*288bf522SAndroid Build Coastguard Worker 129*288bf522SAndroid Build Coastguard Worker Security.insertProviderAt((Provider) o, 1); 130*288bf522SAndroid Build Coastguard Worker } 131*288bf522SAndroid Build Coastguard Worker pemToDer(String pem)132*288bf522SAndroid Build Coastguard Worker static byte[] pemToDer(String pem) throws Exception { 133*288bf522SAndroid Build Coastguard Worker pem = pem.replaceAll("^-.*", ""); 134*288bf522SAndroid Build Coastguard Worker String base64_der = pem.replaceAll("-.*$", ""); 135*288bf522SAndroid Build Coastguard Worker return Base64.decode(base64_der); 136*288bf522SAndroid Build Coastguard Worker } 137*288bf522SAndroid Build Coastguard Worker decryptPrivateKey(byte[] encryptedPrivateKey)138*288bf522SAndroid Build Coastguard Worker private static PKCS8EncodedKeySpec decryptPrivateKey(byte[] encryptedPrivateKey) 139*288bf522SAndroid Build Coastguard Worker throws GeneralSecurityException { 140*288bf522SAndroid Build Coastguard Worker EncryptedPrivateKeyInfo epkInfo; 141*288bf522SAndroid Build Coastguard Worker try { 142*288bf522SAndroid Build Coastguard Worker epkInfo = new EncryptedPrivateKeyInfo(encryptedPrivateKey); 143*288bf522SAndroid Build Coastguard Worker } catch (IOException ex) { 144*288bf522SAndroid Build Coastguard Worker // Probably not an encrypted key. 145*288bf522SAndroid Build Coastguard Worker return null; 146*288bf522SAndroid Build Coastguard Worker } 147*288bf522SAndroid Build Coastguard Worker 148*288bf522SAndroid Build Coastguard Worker char[] password = System.console().readPassword("Password for the private key file: "); 149*288bf522SAndroid Build Coastguard Worker 150*288bf522SAndroid Build Coastguard Worker SecretKeyFactory skFactory = SecretKeyFactory.getInstance(epkInfo.getAlgName()); 151*288bf522SAndroid Build Coastguard Worker Key key = skFactory.generateSecret(new PBEKeySpec(password)); 152*288bf522SAndroid Build Coastguard Worker Arrays.fill(password, '\0'); 153*288bf522SAndroid Build Coastguard Worker 154*288bf522SAndroid Build Coastguard Worker Cipher cipher = Cipher.getInstance(epkInfo.getAlgName()); 155*288bf522SAndroid Build Coastguard Worker cipher.init(Cipher.DECRYPT_MODE, key, epkInfo.getAlgParameters()); 156*288bf522SAndroid Build Coastguard Worker 157*288bf522SAndroid Build Coastguard Worker try { 158*288bf522SAndroid Build Coastguard Worker return epkInfo.getKeySpec(cipher); 159*288bf522SAndroid Build Coastguard Worker } catch (InvalidKeySpecException ex) { 160*288bf522SAndroid Build Coastguard Worker System.err.println("Password may be bad."); 161*288bf522SAndroid Build Coastguard Worker throw ex; 162*288bf522SAndroid Build Coastguard Worker } 163*288bf522SAndroid Build Coastguard Worker } 164*288bf522SAndroid Build Coastguard Worker loadDERPrivateKey(byte[] der)165*288bf522SAndroid Build Coastguard Worker static PrivateKey loadDERPrivateKey(byte[] der) throws Exception { 166*288bf522SAndroid Build Coastguard Worker PKCS8EncodedKeySpec spec = decryptPrivateKey(der); 167*288bf522SAndroid Build Coastguard Worker 168*288bf522SAndroid Build Coastguard Worker if (spec == null) { 169*288bf522SAndroid Build Coastguard Worker spec = new PKCS8EncodedKeySpec(der); 170*288bf522SAndroid Build Coastguard Worker } 171*288bf522SAndroid Build Coastguard Worker 172*288bf522SAndroid Build Coastguard Worker ASN1InputStream bIn = new ASN1InputStream(new ByteArrayInputStream(spec.getEncoded())); 173*288bf522SAndroid Build Coastguard Worker PrivateKeyInfo pki = PrivateKeyInfo.getInstance(bIn.readObject()); 174*288bf522SAndroid Build Coastguard Worker String algOid = pki.getPrivateKeyAlgorithm().getAlgorithm().getId(); 175*288bf522SAndroid Build Coastguard Worker 176*288bf522SAndroid Build Coastguard Worker return KeyFactory.getInstance(algOid).generatePrivate(spec); 177*288bf522SAndroid Build Coastguard Worker } 178*288bf522SAndroid Build Coastguard Worker loadPEMPrivateKey(byte[] pem)179*288bf522SAndroid Build Coastguard Worker static PrivateKey loadPEMPrivateKey(byte[] pem) throws Exception { 180*288bf522SAndroid Build Coastguard Worker byte[] der = pemToDer(new String(pem)); 181*288bf522SAndroid Build Coastguard Worker return loadDERPrivateKey(der); 182*288bf522SAndroid Build Coastguard Worker } 183*288bf522SAndroid Build Coastguard Worker loadPEMPrivateKeyFromFile(String keyFname)184*288bf522SAndroid Build Coastguard Worker static PrivateKey loadPEMPrivateKeyFromFile(String keyFname) throws Exception { 185*288bf522SAndroid Build Coastguard Worker return loadPEMPrivateKey(read(keyFname)); 186*288bf522SAndroid Build Coastguard Worker } 187*288bf522SAndroid Build Coastguard Worker loadDERPrivateKeyFromFile(String keyFname)188*288bf522SAndroid Build Coastguard Worker static PrivateKey loadDERPrivateKeyFromFile(String keyFname) throws Exception { 189*288bf522SAndroid Build Coastguard Worker return loadDERPrivateKey(read(keyFname)); 190*288bf522SAndroid Build Coastguard Worker } 191*288bf522SAndroid Build Coastguard Worker loadDERPublicKey(byte[] der)192*288bf522SAndroid Build Coastguard Worker static PublicKey loadDERPublicKey(byte[] der) throws Exception { 193*288bf522SAndroid Build Coastguard Worker X509EncodedKeySpec publicKeySpec = new X509EncodedKeySpec(der); 194*288bf522SAndroid Build Coastguard Worker KeyFactory factory = KeyFactory.getInstance("RSA"); 195*288bf522SAndroid Build Coastguard Worker return factory.generatePublic(publicKeySpec); 196*288bf522SAndroid Build Coastguard Worker } 197*288bf522SAndroid Build Coastguard Worker loadPEMPublicKey(byte[] pem)198*288bf522SAndroid Build Coastguard Worker static PublicKey loadPEMPublicKey(byte[] pem) throws Exception { 199*288bf522SAndroid Build Coastguard Worker byte[] der = pemToDer(new String(pem)); 200*288bf522SAndroid Build Coastguard Worker X509EncodedKeySpec publicKeySpec = new X509EncodedKeySpec(der); 201*288bf522SAndroid Build Coastguard Worker KeyFactory factory = KeyFactory.getInstance("RSA"); 202*288bf522SAndroid Build Coastguard Worker return factory.generatePublic(publicKeySpec); 203*288bf522SAndroid Build Coastguard Worker } 204*288bf522SAndroid Build Coastguard Worker loadPEMPublicKeyFromFile(String keyFname)205*288bf522SAndroid Build Coastguard Worker static PublicKey loadPEMPublicKeyFromFile(String keyFname) throws Exception { 206*288bf522SAndroid Build Coastguard Worker return loadPEMPublicKey(read(keyFname)); 207*288bf522SAndroid Build Coastguard Worker } 208*288bf522SAndroid Build Coastguard Worker loadDERPublicKeyFromFile(String keyFname)209*288bf522SAndroid Build Coastguard Worker static PublicKey loadDERPublicKeyFromFile(String keyFname) throws Exception { 210*288bf522SAndroid Build Coastguard Worker return loadDERPublicKey(read(keyFname)); 211*288bf522SAndroid Build Coastguard Worker } 212*288bf522SAndroid Build Coastguard Worker loadPEMCertificate(String fname)213*288bf522SAndroid Build Coastguard Worker static X509Certificate loadPEMCertificate(String fname) throws Exception { 214*288bf522SAndroid Build Coastguard Worker try (FileInputStream fis = new FileInputStream(fname)) { 215*288bf522SAndroid Build Coastguard Worker CertificateFactory cf = CertificateFactory.getInstance("X.509"); 216*288bf522SAndroid Build Coastguard Worker return (X509Certificate) cf.generateCertificate(fis); 217*288bf522SAndroid Build Coastguard Worker } 218*288bf522SAndroid Build Coastguard Worker } 219*288bf522SAndroid Build Coastguard Worker getSignatureAlgorithm(Key key)220*288bf522SAndroid Build Coastguard Worker private static String getSignatureAlgorithm(Key key) throws Exception { 221*288bf522SAndroid Build Coastguard Worker if ("EC".equals(key.getAlgorithm())) { 222*288bf522SAndroid Build Coastguard Worker int curveSize; 223*288bf522SAndroid Build Coastguard Worker KeyFactory factory = KeyFactory.getInstance("EC"); 224*288bf522SAndroid Build Coastguard Worker 225*288bf522SAndroid Build Coastguard Worker if (key instanceof PublicKey) { 226*288bf522SAndroid Build Coastguard Worker ECPublicKeySpec spec = factory.getKeySpec(key, ECPublicKeySpec.class); 227*288bf522SAndroid Build Coastguard Worker curveSize = spec.getParams().getCurve().getField().getFieldSize(); 228*288bf522SAndroid Build Coastguard Worker } else if (key instanceof PrivateKey) { 229*288bf522SAndroid Build Coastguard Worker ECPrivateKeySpec spec = factory.getKeySpec(key, ECPrivateKeySpec.class); 230*288bf522SAndroid Build Coastguard Worker curveSize = spec.getParams().getCurve().getField().getFieldSize(); 231*288bf522SAndroid Build Coastguard Worker } else { 232*288bf522SAndroid Build Coastguard Worker throw new InvalidKeySpecException(); 233*288bf522SAndroid Build Coastguard Worker } 234*288bf522SAndroid Build Coastguard Worker 235*288bf522SAndroid Build Coastguard Worker if (curveSize <= 256) { 236*288bf522SAndroid Build Coastguard Worker return "SHA256withECDSA"; 237*288bf522SAndroid Build Coastguard Worker } else if (curveSize <= 384) { 238*288bf522SAndroid Build Coastguard Worker return "SHA384withECDSA"; 239*288bf522SAndroid Build Coastguard Worker } else { 240*288bf522SAndroid Build Coastguard Worker return "SHA512withECDSA"; 241*288bf522SAndroid Build Coastguard Worker } 242*288bf522SAndroid Build Coastguard Worker } else if ("RSA".equals(key.getAlgorithm())) { 243*288bf522SAndroid Build Coastguard Worker return "SHA256withRSA"; 244*288bf522SAndroid Build Coastguard Worker } else { 245*288bf522SAndroid Build Coastguard Worker throw new IllegalArgumentException("Unsupported key type " + key.getAlgorithm()); 246*288bf522SAndroid Build Coastguard Worker } 247*288bf522SAndroid Build Coastguard Worker } 248*288bf522SAndroid Build Coastguard Worker getSignatureAlgorithmIdentifier(Key key)249*288bf522SAndroid Build Coastguard Worker static AlgorithmIdentifier getSignatureAlgorithmIdentifier(Key key) throws Exception { 250*288bf522SAndroid Build Coastguard Worker String id = ALG_TO_ID.get(getSignatureAlgorithm(key)); 251*288bf522SAndroid Build Coastguard Worker 252*288bf522SAndroid Build Coastguard Worker if (id == null) { 253*288bf522SAndroid Build Coastguard Worker throw new IllegalArgumentException("Unsupported key type " + key.getAlgorithm()); 254*288bf522SAndroid Build Coastguard Worker } 255*288bf522SAndroid Build Coastguard Worker 256*288bf522SAndroid Build Coastguard Worker return new AlgorithmIdentifier(new ASN1ObjectIdentifier(id)); 257*288bf522SAndroid Build Coastguard Worker } 258*288bf522SAndroid Build Coastguard Worker verify(PublicKey key, byte[] input, byte[] signature, AlgorithmIdentifier algId)259*288bf522SAndroid Build Coastguard Worker static boolean verify(PublicKey key, byte[] input, byte[] signature, 260*288bf522SAndroid Build Coastguard Worker AlgorithmIdentifier algId) throws Exception { 261*288bf522SAndroid Build Coastguard Worker String algName = ID_TO_ALG.get(algId.getAlgorithm().getId()); 262*288bf522SAndroid Build Coastguard Worker 263*288bf522SAndroid Build Coastguard Worker if (algName == null) { 264*288bf522SAndroid Build Coastguard Worker throw new IllegalArgumentException("Unsupported algorithm " + algId.getAlgorithm()); 265*288bf522SAndroid Build Coastguard Worker } 266*288bf522SAndroid Build Coastguard Worker 267*288bf522SAndroid Build Coastguard Worker Signature verifier = Signature.getInstance(algName); 268*288bf522SAndroid Build Coastguard Worker verifier.initVerify(key); 269*288bf522SAndroid Build Coastguard Worker verifier.update(input); 270*288bf522SAndroid Build Coastguard Worker 271*288bf522SAndroid Build Coastguard Worker return verifier.verify(signature); 272*288bf522SAndroid Build Coastguard Worker } 273*288bf522SAndroid Build Coastguard Worker sign(PrivateKey privateKey, byte[] input)274*288bf522SAndroid Build Coastguard Worker static byte[] sign(PrivateKey privateKey, byte[] input) throws Exception { 275*288bf522SAndroid Build Coastguard Worker Signature signer = Signature.getInstance(getSignatureAlgorithm(privateKey)); 276*288bf522SAndroid Build Coastguard Worker signer.initSign(privateKey); 277*288bf522SAndroid Build Coastguard Worker signer.update(input); 278*288bf522SAndroid Build Coastguard Worker return signer.sign(); 279*288bf522SAndroid Build Coastguard Worker } 280*288bf522SAndroid Build Coastguard Worker read(String fname)281*288bf522SAndroid Build Coastguard Worker static byte[] read(String fname) throws Exception { 282*288bf522SAndroid Build Coastguard Worker long offset = 0; 283*288bf522SAndroid Build Coastguard Worker File f = new File(fname); 284*288bf522SAndroid Build Coastguard Worker long length = f.length(); 285*288bf522SAndroid Build Coastguard Worker byte[] image = new byte[(int)length]; 286*288bf522SAndroid Build Coastguard Worker FileInputStream fis = new FileInputStream(f); 287*288bf522SAndroid Build Coastguard Worker while (offset < length) { 288*288bf522SAndroid Build Coastguard Worker offset += fis.read(image, (int)offset, (int)(length - offset)); 289*288bf522SAndroid Build Coastguard Worker } 290*288bf522SAndroid Build Coastguard Worker fis.close(); 291*288bf522SAndroid Build Coastguard Worker return image; 292*288bf522SAndroid Build Coastguard Worker } 293*288bf522SAndroid Build Coastguard Worker write(byte[] data, String fname)294*288bf522SAndroid Build Coastguard Worker static void write(byte[] data, String fname) throws Exception{ 295*288bf522SAndroid Build Coastguard Worker FileOutputStream out = new FileOutputStream(fname); 296*288bf522SAndroid Build Coastguard Worker out.write(data); 297*288bf522SAndroid Build Coastguard Worker out.close(); 298*288bf522SAndroid Build Coastguard Worker } 299*288bf522SAndroid Build Coastguard Worker } 300