今天在網上看到一個java公私密鑰演算法。很不錯。。。
添加要簽名的資訊public final byte[] sign()throws SignatureException返回簽名的數組,前提是initSign和updatepublic final void initVerify(PublicKey publicKey)throws InvalidKeyException用指定的公開金鑰初始化參數:publicKey 驗證時用的公開金鑰public final boolean verify(byte[] signature)throws SignatureException驗證簽名是否有效,前提是已經initVerify初始化參數: signature 簽名數組 */import java.security.*;import java.security.spec.*;public class testdsa { public static void main(String[] args) throws java.security.NoSuchAlgorithmException,java.lang.Exception { testdsa my=new testdsa(); my.run(); } public void run() { //數位簽章產生密鑰 //第一步產生金鑰組,如果已經產生過,本過程就可以跳過,對使用者來講myprikey.dat要儲存在本地 //而mypubkey.dat給發布給其它使用者 if ((new java.io.File("myprikey.dat")).exists()==false) { if (generatekey()==false) { System.out.println("產生金鑰組敗"); return; }; }//第二步,此使用者//從檔案中讀入私密金鑰,對一個字串進行簽名後儲存在一個檔案(myinfo.dat)中//並且再把myinfo.dat發送出去//為了方便數位簽章也放進了myifno.dat檔案中,當然也可分別發送 try { java.io.ObjectInputStream in=new java.io.ObjectInputStream(new java.io.FileInputStream("myprikey.dat")); PrivateKey myprikey=(PrivateKey)in.readObject(); in.close();// java.security.spec.X509EncodedKeySpec pubX509=new java.security.spec.X509EncodedKeySpec(bX509);//java.security.spec.X509EncodedKeySpec pubkeyEncode=java.security.spec.X509EncodedKeySpec String myinfo="這是我的資訊"; //要簽名的資訊 //用私密金鑰對資訊產生數位簽章 java.security.Signature signet=java.security.Signature.getInstance("DSA"); signet.initSign(myprikey); signet.update(myinfo.getBytes()); byte[] signed=signet.sign(); //對資訊的數位簽章 System.out.println("signed(簽名內容)="+byte2hex(signed));//把資訊和數位簽章儲存在一個檔案中 java.io.ObjectOutputStream out=new java.io.ObjectOutputStream(new java.io.FileOutputStream("myinfo.dat")); out.writeObject(myinfo); out.writeObject(signed); out.close(); System.out.println("簽名並組建檔案成功"); } catch (java.lang.Exception e) { e.printStackTrace(); System.out.println("簽名並組建檔案失敗"); }; //第三步 //其他人通過公用方式得到此戶的公開金鑰和檔案 //其他人用此戶的公開金鑰,對檔案進行檢查,如果成功說明是此使用者發布的資訊. // try { java.io.ObjectInputStream in=new java.io.ObjectInputStream(new java.io.FileInputStream("mypubkey.dat")); PublicKey pubkey=(PublicKey)in.readObject(); in.close(); System.out.println(pubkey.getFormat()); in=new java.io.ObjectInputStream(new java.io.FileInputStream("myinfo.dat")); String info=(String)in.readObject(); byte[] signed=(byte[])in.readObject(); in.close(); java.security.Signature signetcheck=java.security.Signature.getInstance("DSA"); signetcheck.initVerify(pubkey); signetcheck.update(info.getBytes()); if (signetcheck.verify(signed)) { System.out.println("info="+info); System.out.println("簽名正常"); } else System.out.println("非簽名正常"); } catch (java.lang.Exception e) {e.printStackTrace();}; } //產生一對檔案myprikey.dat和mypubkey.dat---私密金鑰和公開金鑰, //公開金鑰要使用者發送(檔案,網路等方法)給其它使用者,私密金鑰儲存在本地 public boolean generatekey() { try { java.security.KeyPairGenerator keygen=java.security.KeyPairGenerator.getInstance("DSA");// SecureRandom secrand=new SecureRandom();// secrand.setSeed("tttt".getBytes()); //初始化隨機產生器// keygen.initialize(576,secrand); //初始化金鑰產生器 keygen.initialize(512); KeyPair keys=keygen.genKeyPair();// KeyPair keys=keygen.generateKeyPair(); //產生密鑰組 PublicKey pubkey=keys.getPublic(); PrivateKey prikey=keys.getPrivate(); java.io.ObjectOutputStream out=new java.io.ObjectOutputStream(new java.io.FileOutputStream("myprikey.dat")); out.writeObject(prikey); out.close(); System.out.println("寫入對象 prikeys ok"); out=new java.io.ObjectOutputStream(new java.io.FileOutputStream("mypubkey.dat")); out.writeObject(pubkey); out.close(); System.out.println("寫入對象 pubkeys ok"); System.out.println("產生金鑰組成功"); return true; } catch (java.lang.Exception e) { e.printStackTrace(); System.out.println("產生金鑰組失敗"); return false; }; } public String byte2hex(byte[] b) { String hs=""; String stmp=""; for (int n=0;n