package com.ivan.security.algorithm;
/**
* 对文件进行DSA数字签名
* @author Ivan
* @DataTime 2006-12-12 0:58
*
*/
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.security.InvalidKeyException;
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.SecureRandom;
import java.security.Signature;
import java.security.SignatureException;
import com.iuxi.security.util.Tool;
public class DSAUtil ...{
private PublicKey pubKey;
private PrivateKey priKey;
public String pubfile = "";
public String prifile = "";
public DSAUtil() ...{}
public DSAUtil(String pubfile, String prifile) ...{
this.pubfile = pubfile;
this.prifile = prifile;
}
/** *//**
* 采用DSA算法生成非对称密钥对
*
*/
public void genKeys() ...{
try ...{
KeyPairGenerator keygen = KeyPairGenerator.getInstance("DSA");
SecureRandom secrand = new SecureRandom();
secrand.setSeed("random generator".getBytes());
keygen.initialize(512,secrand); //初始化密钥生成器
KeyPair keys = keygen.generateKeyPair();//生成密钥对
pubKey = keys.getPublic();
priKey = keys.getPrivate();
}catch(NoSuchAlgorithmException ex) ...{
ex.printStackTrace();
}
}
public String getPrifile() ...{
return prifile;
}
public void setPrifile(String prifile) ...{
this.prifile = prifile;
}
public String getPubfile() ...{
return pubfile;
}
public void setPubfile(String pubfile) ...{
this.pubfile = pubfile;
}
/** *//**
* 保存密钥对信息到磁盘
* @param filepath1 公钥的存放路径
* @param filepath2 私钥的存放路径
*/
public void saveKeys() ...{
if((!pubfile.equals(""))&&(!prifile.equals("")))
this.saveKeys(pubfile,prifile);
else
System.err.println("保存密钥出错,请先设置保存路径!");
}
public void saveKeys(String filepath1, String filepath2) ...{
try ...{
FileOutputStream fos = new FileOutputStream(filepath1);
ObjectOutputStream oos = new ObjectOutputStream(fos);
oos.writeObject(pubKey);
oos.close();
fos = new FileOutputStream(filepath2);
oos = new ObjectOutputStream(fos);
oos.writeObject(priKey);
oos.close();
}catch(IOException ex) ...{
System.err.println("保存密钥对信息出错!");
ex.printStackTrace();
}
}
/** *//**
* 从磁盘读取密钥信息
* @param filepath 密钥存放路径
* @return 返回密钥信息,为 Object 类,然后可根据具体的 PublicKey 或 PrivateKey 进行强制类型转换
*/
private Object getKey(String filepath) ...{
Object obj = null;
try ...{
FileInputStream fis = new FileInputStream(filepath);
ObjectInputStream ois = new ObjectInputStream(fis);
obj = ois.readObject();
ois.close();
}catch(IOException ex) ...{
System.err.println("读取密钥信息错误!");
}catch(ClassNotFoundException ex) ...{
ex.printStackTrace();
}
return obj;
}
/** *//**
* 获取公钥,如果当前公钥为空,则从磁盘文件读取,并将其设置为当前公钥,否则直接返回当前公钥
* @return 公钥
*/
public PublicKey getPubKey() ...{
if(pubKey != null)
return pubKey;
if(!pubfile.equals("")) ...{
pubKey = (PublicKey)this.getKey(pubfile);
return this.pubKey;
}
else ...{
System.err.println("读取公钥信息错误!");
return null;
}
}
public PublicKey getPubKey(String filepath) ...{
pubKey = (PublicKey)this.getKey(filepath);
return this.pubKey;
}
/** *//**
* 获取私钥,如果当前私钥为空,则从磁盘文件读取,并将其设置为当前私钥,否则直接返回当前私钥
* @return 私钥
*/
public PrivateKey getPriKey() ...{
if(priKey != null)
return priKey;
if(!prifile.equals("")) ...{
priKey = (PrivateKey)this.getKey(pubfile);
return this.priKey;
}
else ...{
System.err.println("读取私钥信息错误!");
return null;
}
}
public PrivateKey getPriKey(String filepath) ...{
priKey = (PrivateKey)this.getKey(filepath);
return this.priKey;
}
/** *//**
* 利用当前私钥对信息进行签名
* @return 签名信息(byte类型)
*/
public byte[] signBytes(byte[] info) ...{
byte[] signed = null;
if(priKey == null) ...{
System.err.println("======== 提取密钥信息错误,无法完成签名 =========");
return null;
}
try ...{
Signature signet = Signature.getInstance("DSA");
signet.initSign(priKey);
signet.update(info);
signed = signet.sign();
}catch(NoSuchAlgorithmException ex) ...{
ex.printStackTrace();
}catch(InvalidKeyException ex) ...{
System.err.println("签名错误,无效的密钥");
ex.printStackTrace();
}catch(SignatureException ex) ...{
ex.printStackTrace();
}
return signed;
}
/** *//**
* 验证签名信息
* @param info 待验证的信息
* @param signed 该验证信息的签名
* @return 若验证正常,则返回 true , 否则返回 false
*/
public boolean checkSign(byte[] info, byte[] signed) ...{
if(pubKey == null) ...{
System.err.println("======== 提取密钥信息错误,无法完成签名 =========");
return false;
}
try ...{
Signature checkSignet = Signature.getInstance("DSA");
checkSignet.initVerify(pubKey);
checkSignet.update(info);
if(checkSignet.verify(signed)) ...{
System.out.println("======== 签名正常 =========");
return true;
}
else ...{
System.err.println("======== 签名信息异常 =========");
return false;
}
}catch(NoSuchAlgorithmException ex) ...{
ex.printStackTrace();
}catch(InvalidKeyException ex) ...{
System.err.println("验证签名错误,无效的密钥");
ex.printStackTrace();
}catch(SignatureException ex) ...{
ex.printStackTrace();
}
return true;
}
public static void main(String[] args) ...{
DSAUtil dsa = new DSAUtil("pubKey.dat","priKey.dat");
dsa.genKeys();
dsa.saveKeys();
String test = "This is just a test!";
byte[] signedData = dsa.signBytes(test.getBytes());
System.out.println(Tool.byte2hex(signedData));
dsa.checkSign(test.getBytes(),signedData);
}
}
分享到:
相关推荐
总的来说,DSA数字签名算法是网络安全和信息安全的关键组成部分,它通过数学原理确保了数据的完整性和非否认性。理解和掌握DSA的实现与验证方法对于任何从事安全相关工作的IT专业人员来说都是至关重要的。
在提供的压缩包文件中,"DSA数字签名"可能包含了实现这些功能的源代码,这将帮助开发者理解DSA算法的实现细节,学习如何在C语言环境下实现数字签名。这些源代码可能包括了DSA算法的实现函数,如计算签名、验证签名的...
总结,DSA数字签名算法是现代网络安全的重要组成部分,结合MD5或SHA-1等哈希函数,为数据提供了可靠的完整性保护和身份验证。在C语言环境中实现DSA签名,不仅需要理解算法原理,还需要熟悉文件操作和可能涉及的加密...
DSA数字签名广泛应用于电子商务、网络安全、软件授权、文件完整性校验等领域,如HTTPS协议中的SSL/TLS证书、Git版本控制系统的提交验证等。 总的来说,`DSA.zip`文件提供的`DSA.CPP`源代码可能是一个实用的工具,...
总结起来,DSA数字签名在Java中的实现涉及了密钥对生成、签名生成与验证等步骤,这些步骤都是通过`java.security`包中的类和方法完成的。了解并掌握这些知识点,对于开发安全的网络应用程序至关重要。同时,通过阅读...
《深入理解DSA数字签名:C语言实现与SHA哈希算法》 数字签名是现代密码学中的重要组成部分,它在确保信息安全传输、防止篡改和伪造等方面发挥着关键作用。DSA(Digital Signature Algorithm)是由美国国家标准和...
DSA数字签名算法 DSA(Digital Signature Algorithm,数字签名算法)是一种公开密钥算法,用作数字签名标准的一部分。它不能用作加密,只用作数字签名。DSA 使用公开密钥,为接受者验证数据的完整性和数据发送者的...
在C++中实现DSA数字签名涉及到以下几个关键步骤: 1. **密钥生成**:DSA需要一对密钥,包括一个私钥和一个公钥。私钥用于签名,公钥用于验证。首先选择两个大素数p和q,计算它们的乘积n=p*q,并找到一个满足1 且gcd...
DSA签名程序和DSA验证程序。 签名程序流程: a. 读入字符串(从屏幕或文本文件中),字符串内容应包含自己的学号或姓名; ...e. 对第2步产生的SHA-1值进行签名,保存签名到文件中(signature.txt)
DSA数字签名算法 DSA数字签名算法是数字签名标准的一部分,它使用公开密钥算法,不能用作加密,只用作数字签名。DSA算法的安全性基于解离散对数的困难性,这类签字标准具有较大的兼容性和适用性,成为网络安全体系...
在IT领域,尤其是在网络安全和密码学中,RSA和DSA(Digital Signature Algorithm)是两种重要的公钥加密算法,常用于数字签名。数字签名是确保数据完整性和发送者身份验证的关键技术,而C++作为一门强大的系统级编程...
至于工具,除了专业软件如Adobe Acrobat,还有一些免费或开源的工具,如PDFSigner、PDFSam等,它们提供了图形化的界面,让用户可以方便地对PDF进行数字签名操作。 总的来说,PDF文档的数字签名是一个重要的安全特性...
这个名为“DSA 数字签名 C++源代码_1610386222”的压缩包文件很可能包含了用C++实现DSA数字签名的源代码,可以作为学习和研究的参考资料。通过阅读和分析这些代码,你可以更深入地理解DSA算法的工作原理以及如何在...
包涵三个RSA算法,c++是实现,数字签名的合集,三个独自的程序,可以独自编译运行,VC6.0下编译 包涵三个RSA算法,c++是实现,数字签名的合集,三个独自的程序,可以独自编译运行,VC6.0下编译
发送者使用自己的私钥对数据的哈希值进行加密,生成的数字签名附在数据后面。接收者则使用发送者的公钥来解密签名,并重新计算数据的哈希值,如果两者匹配,则证明数据未被篡改且确实来自声称的发送者。 在Office...
以往的文件或书信可以通过亲笔签名来证明其真实性, 而通过计算机网络传输的信息则可以通过数字签名技术来实现其真实性的验证。 下面就以DSA算法为例,介绍数字签名算法。DSA算法在1991年被美国国家标准与技术局...
数字签名是通过一种加密算法,将原始数据(如文本或文件)与发送者的私钥相结合生成的。接收者可以使用发送者的公钥解密这个签名,从而验证数据的完整性和发送者的身份。这种技术基于非对称加密,如RSA或DSA...
(4)验证过程:接收者接收到信息后,使用发送者的公钥和接收到的签名对消息摘要进行验证。如果计算结果与签名匹配,则确认信息未被篡改。 接下来,我们要了解签名和数字信封的一般使用过程。数字签名通常与数字...
对于数字签名,需要先对原始数据进行哈希计算,然后用私钥对哈希值进行加密,生成的加密结果就是数字签名。接收端使用公钥解密数字签名,并重新计算数据的哈希值,对比两者是否一致,从而确认数据的完整性和发送者的...