1 21 22 package net.sourceforge.jcetaglib.lib; 23 24 import net.sourceforge.jcetaglib.exceptions.CryptoException; 25 import net.sourceforge.jcetaglib.tools.FileTools; 26 import net.sourceforge.jcetaglib.tools.KeyTools; 27 import org.bouncycastle.asn1.*; 28 import org.bouncycastle.asn1.misc.MiscObjectIdentifiers; 29 import org.bouncycastle.asn1.misc.NetscapeCertType; 30 import org.bouncycastle.asn1.x509.*; 31 import org.bouncycastle.jce.PKCS10CertificationRequest; 32 import org.bouncycastle.jce.X509Principal; 33 import org.bouncycastle.jce.X509V2CRLGenerator; 34 import org.bouncycastle.jce.X509V3CertificateGenerator; 35 import org.bouncycastle.jce.netscape.NetscapeCertRequest; 36 import org.bouncycastle.jce.provider.BouncyCastleProvider; 37 import org.bouncycastle.util.encoders.Base64; 38 39 import java.io.ByteArrayInputStream ; 40 import java.io.FileInputStream ; 41 import java.io.FileOutputStream ; 42 import java.io.IOException ; 43 import java.math.BigInteger ; 44 import java.security.*; 45 import java.security.cert.Certificate ; 46 import java.security.cert.*; 47 import java.util.Date ; 48 49 50 58 public class X509Cert { 59 60 private static final String NS_CA = "ca"; 61 private static final String NS_SERVER = "server"; 62 private static final String NS_CLIENT = "client"; 63 private static final String NS_ALL = "all"; 64 65 76 public static KeyPair generateKeyPair(String keypairalgorithm 77 , int keylength 78 , byte[] seed) throws NoSuchAlgorithmException, NoSuchProviderException, CryptoException { 79 80 Security.addProvider(new BouncyCastleProvider()); 81 82 KeyPairGenerator g = KeyPairGenerator.getInstance(keypairalgorithm, "BC"); 83 84 SecureRandom sr = Seed.getSecureRandom(seed); 85 86 g.initialize(keylength, sr); 87 return g.generateKeyPair(); 88 } 89 90 103 public static X509Certificate selfsign(PrivateKey privatekey 104 , PublicKey publickey 105 , String signaturealgorithm 106 , long validity 107 , String subjectdn 108 , boolean isca 109 , String netscapeextensions) throws CertificateException { 110 try { 111 Security.addProvider(new BouncyCastleProvider()); 113 114 Date firstDate = new Date (); 115 firstDate.setTime(firstDate.getTime() - 10 * 60 * 1000); 117 Date lastDate = new Date (); 118 lastDate.setTime(lastDate.getTime() + (validity * (24 * 60 * 60 * 1000))); 120 121 X509V3CertificateGenerator v3CertGen = new X509V3CertificateGenerator(); 122 123 byte[] serno = new byte[8]; 125 SecureRandom random = SecureRandom.getInstance("SHA1PRNG"); 126 random.setSeed((new Date ().getTime())); 127 random.nextBytes(serno); 128 129 BigInteger sn = new java.math.BigInteger (serno).abs(); 130 131 v3CertGen.setSerialNumber(sn); 133 v3CertGen.setIssuerDN(new X509Principal(subjectdn)); 134 v3CertGen.setNotBefore(firstDate); 135 v3CertGen.setNotAfter(lastDate); 136 v3CertGen.setSubjectDN(new X509Principal(subjectdn)); 137 v3CertGen.setPublicKey(publickey); 138 v3CertGen.setSignatureAlgorithm(signaturealgorithm); 139 140 v3CertGen.addExtension(X509Extensions.SubjectKeyIdentifier, 142 false, 143 CertTools.createSubjectKeyId(publickey)); 144 145 v3CertGen.addExtension(X509Extensions.BasicConstraints, 146 false, 147 new BasicConstraints(isca)); 148 149 if (NS_CA.equalsIgnoreCase(netscapeextensions)) { 151 v3CertGen.addExtension(MiscObjectIdentifiers.netscapeCertType, 152 false, 153 new NetscapeCertType(NetscapeCertType.sslCA | NetscapeCertType.smimeCA | NetscapeCertType.objectSigningCA)); 154 } else if (NS_SERVER.equalsIgnoreCase(netscapeextensions)) { 155 v3CertGen.addExtension(MiscObjectIdentifiers.netscapeCertType, 156 false, 157 new NetscapeCertType(NetscapeCertType.sslServer)); 158 } else if (NS_CLIENT.equalsIgnoreCase(netscapeextensions)) { 159 v3CertGen.addExtension(MiscObjectIdentifiers.netscapeCertType, 160 false, 161 new NetscapeCertType(NetscapeCertType.sslClient | NetscapeCertType.smime | NetscapeCertType.objectSigning)); 162 } else if (NS_ALL.equalsIgnoreCase(netscapeextensions)) { 163 v3CertGen.addExtension(MiscObjectIdentifiers.netscapeCertType, 164 false, 165 new NetscapeCertType(NetscapeCertType.sslClient | NetscapeCertType.sslServer | NetscapeCertType.smime | NetscapeCertType.objectSigning | NetscapeCertType.sslCA | NetscapeCertType.smimeCA | NetscapeCertType.objectSigningCA)); 166 } 167 168 X509Certificate cert = v3CertGen.generateX509Certificate(privatekey); 170 171 cert.checkValidity(new Date ()); 173 cert.verify(publickey); 175 176 return cert; 177 } catch (Exception e) { 178 e.printStackTrace(); 179 throw new CertificateException(e.getMessage()); 180 } 181 } 182 183 198 public static X509Certificate sign(PublicKey publickey 199 , PrivateKey issuerprivatekey 200 , X509Certificate issuercertificate 201 , String signaturealgorithm 202 , long validity 203 , String subjectdn 204 , boolean isca 205 , String crldisturi 206 , String netscapeextensions) throws CertificateException { 207 try { 208 Security.addProvider(new BouncyCastleProvider()); 210 211 Date firstDate = new Date (); 212 firstDate.setTime(firstDate.getTime() - 10 * 60 * 1000); 214 Date lastDate = new Date (); 215 lastDate.setTime(lastDate.getTime() + (validity * (24 * 60 * 60 * 1000))); 217 218 X509V3CertificateGenerator v3CertGen = new X509V3CertificateGenerator(); 219 220 byte[] serno = new byte[8]; 222 SecureRandom random = SecureRandom.getInstance("SHA1PRNG"); 223 random.setSeed((new Date ().getTime())); 224 random.nextBytes(serno); 225 226 BigInteger sn = new java.math.BigInteger (serno).abs(); 227 String issuerDN = issuercertificate.getSubjectDN().toString(); 228 229 v3CertGen.setSerialNumber(sn); 231 v3CertGen.setIssuerDN(new X509Principal(issuerDN)); 232 v3CertGen.setNotBefore(firstDate); 233 v3CertGen.setNotAfter(lastDate); 234 v3CertGen.setSubjectDN(new X509Principal(subjectdn)); 235 v3CertGen.setPublicKey(publickey); 236 v3CertGen.setSignatureAlgorithm(signaturealgorithm); 237 238 v3CertGen.addExtension(X509Extensions.SubjectKeyIdentifier, 240 false, 241 CertTools.createSubjectKeyId(publickey)); 242 243 v3CertGen.addExtension(X509Extensions.AuthorityKeyIdentifier, 244 false, 245 CertTools.createAuthorityKeyId(issuercertificate.getPublicKey())); 246 247 v3CertGen.addExtension(X509Extensions.BasicConstraints, 248 false, 249 new BasicConstraints(isca)); 250 251 if (crldisturi != null && !crldisturi.equalsIgnoreCase("")) { 253 GeneralName gn = new GeneralName(new DERIA5String(crldisturi), 6); 254 DERSequence seq = new DERSequence(gn); 255 GeneralNames gns = new GeneralNames(seq); 256 DistributionPointName dpn = new DistributionPointName(0, gns); 257 DistributionPoint distp = new DistributionPoint(dpn, null, null); 258 v3CertGen.addExtension(X509Extensions.CRLDistributionPoints.getId(), false, distp); 259 } 260 261 if (NS_CA.equalsIgnoreCase(netscapeextensions)) { 263 v3CertGen.addExtension(MiscObjectIdentifiers.netscapeCertType, 264 false, 265 new NetscapeCertType(NetscapeCertType.sslCA | NetscapeCertType.smimeCA | NetscapeCertType.objectSigningCA)); 266 } else if (NS_SERVER.equalsIgnoreCase(netscapeextensions)) { 267 v3CertGen.addExtension(MiscObjectIdentifiers.netscapeCertType, 268 false, 269 new NetscapeCertType(NetscapeCertType.sslServer)); 270 } else if (NS_CLIENT.equalsIgnoreCase(netscapeextensions)) { 271 v3CertGen.addExtension(MiscObjectIdentifiers.netscapeCertType, 272 false, 273 new NetscapeCertType(NetscapeCertType.sslClient | NetscapeCertType.smime | NetscapeCertType.objectSigning)); 274 } else if (NS_ALL.equalsIgnoreCase(netscapeextensions)) { 275 v3CertGen.addExtension(MiscObjectIdentifiers.netscapeCertType, 276 false, 277 new NetscapeCertType(NetscapeCertType.sslClient | NetscapeCertType.sslServer | NetscapeCertType.smime | NetscapeCertType.objectSigning | NetscapeCertType.sslCA | NetscapeCertType.smimeCA | NetscapeCertType.objectSigningCA)); 278 } 279 280 X509Certificate cert = v3CertGen.generateX509Certificate(issuerprivatekey); 282 283 cert.checkValidity(new Date ()); 285 cert.verify(issuercertificate.getPublicKey()); 287 288 return cert; 289 } catch (Exception e) { 290 e.printStackTrace(); 291 throw new CertificateException(e.getMessage()); 292 } 293 } 294 295 307 public static X509CRL CreateCRL(BigInteger [] certserialnumbers 308 , int crlnumber 309 , long crlperiod 310 , String signaturealgorithm 311 , X509Certificate cacert 312 , PrivateKey caprivkey) throws CertificateException { 313 X509CRL crl = null; 314 try { 315 Security.addProvider(new BouncyCastleProvider()); 317 318 Date thisUpdate = new Date (); 319 Date nextUpdate = new Date (); 320 nextUpdate.setTime(nextUpdate.getTime() + (crlperiod * 60 * 60 * 1000)); 322 323 X509V2CRLGenerator crlgen = new X509V2CRLGenerator(); 324 crlgen.setThisUpdate(thisUpdate); 325 crlgen.setNextUpdate(nextUpdate); 326 crlgen.setSignatureAlgorithm(signaturealgorithm); 327 328 crlgen.setIssuerDN(new X509Principal(cacert.getSubjectDN().toString())); 330 331 for (int i = 0; i < certserialnumbers.length; i++) { 332 crlgen.addCRLEntry(certserialnumbers[i], thisUpdate, 0); 333 } 334 335 crlgen.addExtension(X509Extensions.AuthorityKeyIdentifier, 336 false, 337 CertTools.createAuthorityKeyId(cacert.getPublicKey())); 338 339 CRLNumber crlnum = new CRLNumber(BigInteger.valueOf(crlnumber)); 340 crlgen.addExtension(X509Extensions.CRLNumber.getId(), false, crlnum); 341 342 crl = crlgen.generateX509CRL(caprivkey); 343 344 return crl; 345 } catch (Exception e) { 346 e.printStackTrace(); 347 throw new CertificateException(e.getMessage()); 348 } 349 } 350 351 360 public static String verifyCertificate(X509Certificate cert 361 , X509Certificate cacert 362 , X509CRL crl) throws CertificateException { 363 364 String status = "INVALID"; 365 366 try { 367 if (crl.isRevoked(cert)) { 368 status = "REVOKED"; 369 } else { 370 try { 371 cert.checkValidity(new Date ()); 372 } catch (Exception vae) { 373 status = "EXPIRED"; 374 } 375 376 if (!status.equals("EXPIRED")) { 377 try { 378 cert.verify(cacert.getPublicKey()); 379 status = "VERIFIED"; 380 } catch (Exception vee) { 381 status = "INVALID"; 382 } 383 } 384 } 385 386 return status; 387 } catch (Exception e) { 388 e.printStackTrace(); 389 throw new CertificateException(e.getMessage()); 390 } 391 } 392 393 400 public static String getCertificateAsPem(X509Certificate cert) throws CertificateEncodingException { 401 402 byte output[] = cert.getEncoded(); 403 byte certB64[] = Base64.encode(output); 404 405 return "-----BEGIN CERTIFICATE-----\n" + new String (certB64) + "\n-----END CERTIFICATE-----"; 406 } 407 408 414 public static String getPrivateAsPem(PrivateKey privatekey) { 415 416 byte output[] = privatekey.getEncoded(); 417 byte certB64[] = Base64.encode(output); 418 419 return "-----BEGIN PRIVATE KEY-----\n" + new String (certB64) + "\n-----END PRIVATE KEY-----"; 420 } 421 422 435 public static void saveAsP12(X509Certificate cert 436 , X509Certificate signedby 437 , PrivateKey privatekey 438 , String keystore 439 , String entryname 440 , StringBuffer password) throws KeyStoreException, NoSuchProviderException, Exception { 441 442 KeyStore store = KeyStore.getInstance("PKCS12", "BC"); 444 445 store = KeyTools.createP12(entryname, privatekey, cert, signedby); 446 store.store(new FileOutputStream (keystore), password.toString().toCharArray()); 447 } 448 449 462 public static X509Certificate getCertificateFromP12(String keystore 463 , String entryname 464 , StringBuffer password) throws KeyStoreException, NoSuchAlgorithmException, NoSuchProviderException, IOException , CertificateException { 465 KeyStore store = KeyStore.getInstance("PKCS12", "BC"); 467 store.load(new FileInputStream (keystore), password.toString().toCharArray()); 468 469 Certificate [] certchain = KeyTools.getCertChain(store, entryname); 470 return (X509Certificate) certchain[0]; 471 } 472 473 486 public static X509Certificate getCACertificateFromP12(String keystore 487 , String entryname 488 , StringBuffer password) throws KeyStoreException, NoSuchAlgorithmException, NoSuchProviderException, IOException , CertificateException { 489 KeyStore store = KeyStore.getInstance("PKCS12", "BC"); 491 store.load(new FileInputStream (keystore), password.toString().toCharArray()); 492 493 Certificate [] certchain = KeyTools.getCertChain(store, entryname); 494 return (X509Certificate) certchain[certchain.length - 1]; 495 } 496 497 511 public static PrivateKey getPrivateFromP12(String keystore 512 , String entryname 513 , StringBuffer password) throws KeyStoreException, NoSuchAlgorithmException, NoSuchProviderException, IOException , CertificateException, UnrecoverableKeyException { 514 KeyStore store = KeyStore.getInstance("PKCS12", "BC"); 516 store.load(new FileInputStream (keystore), password.toString().toCharArray()); 517 518 return (PrivateKey) store.getKey(entryname, password.toString().toCharArray()); 519 } 520 521 529 public static String replace(String text, String repl, String with) { 530 if (text == null) { 531 return null; 532 } 533 534 StringBuffer buf = new StringBuffer (text.length()); 535 int start = 0, end = 0; 536 while ((end = text.indexOf(repl, start)) != -1) { 537 buf.append(text.substring(start, end)).append(with); 538 start = end + repl.length(); 539 } 540 buf.append(text.substring(start)); 541 return buf.toString(); 542 } 543 544 551 public static PKCS10CertificationRequest getPKCS10Request(String request) throws CertificateException { 552 553 byte[] buffer; 554 555 PKCS10CertificationRequest pkcs10 = null; 556 557 try { 558 try { 559 String beginKey = "-----BEGIN CERTIFICATE REQUEST-----"; 561 String endKey = "-----END CERTIFICATE REQUEST-----"; 562 buffer = FileTools.getBytesFromPEM(request.getBytes(), beginKey, endKey); 563 } catch (IOException e) { 564 try { 565 String beginKey = "-----BEGIN NEW CERTIFICATE REQUEST-----"; 567 String endKey = "-----END NEW CERTIFICATE REQUEST-----"; 568 buffer = FileTools.getBytesFromPEM(request.getBytes(), beginKey, endKey); 569 } catch (IOException ioe) { 570 572 request = replace(request, "\n", ""); 575 request = replace(request, "\r", ""); 576 577 buffer = Base64.decode(request.getBytes()); 578 } 579 } 580 581 DERObject derobj = new DERInputStream(new ByteArrayInputStream (buffer)).readObject(); 582 ASN1Sequence seq = (ASN1Sequence) derobj; 583 pkcs10 = new PKCS10CertificationRequest(seq); 584 585 if (pkcs10.verify() == false) { 586 throw new CertificateException("Not a valid PKCS10 request"); 587 } 588 589 return pkcs10; 590 591 } catch (Exception e) { 592 e.printStackTrace(); 593 throw new CertificateException(e.getMessage()); 594 } 595 } 596 597 604 public static NetscapeCertRequest getNetscapeRequest(String request) throws CertificateException { 605 byte[] buffer; 606 607 NetscapeCertRequest nscr = null; 608 609 try { 610 request = replace(request, "\n", ""); 613 request = replace(request, "\r", ""); 614 615 buffer = Base64.decode(request.getBytes()); 616 617 DERInputStream in = new DERInputStream(new ByteArrayInputStream (buffer)); 618 DERSequence spkac = (DERSequence) in.readObject(); 619 nscr = new NetscapeCertRequest(spkac); 620 621 nscr.setChallenge("challenge"); 622 if (nscr.verify("challenge") == false) { 623 throw new CertificateException("Not a valid Netscape request"); 624 } 625 626 return nscr; 627 628 } catch (Exception e) { 629 e.printStackTrace(); 630 throw new CertificateException(e.getMessage()); 631 } 632 } 633 } 634 | Popular Tags |