一、概述
SHA算法基于MD4算法基础之上,作为MD算法的继任者,成为新一代消息摘要算法的代表。SHA与MD算法不同之处主要在于摘要长度,SHA算法的摘要长度更长,安全性更高。
SHA(Secure Hash Algorithm,安全散列算法)是消息摘要算法的一种,被广泛认可的MD5算法的继任者。SHA算法家族目前共有SHA-0、SHA-1、SHA-224、SHA-256、SHA-384和SHA-512五种算法,通常将后四种算法并称为SHA-2算法。
SHA算法发展:
SHA-0算法:
SHA-0是在1993年发布的,但由于最后发现SHA-0算法中含有会降低密码安全性的错误被收回。
SHA-1算法:
1995年,发布了SHA-1算法,通常我们把SHA-1算法简称为SHA算法。SHA-1算法在许多安全协定中广为使用,包括TLS/SSL、PGP、SSH、S/MIME和IPsec,曾被视为是MD5算法的后继者。SHA-0和SHA-1算法可对最大长度为264的字节信息做摘要处理,得到一个160的摘要信息,其设计原理相似于MD4和MD5算法。如果将得到160位的摘要信息换算成十六进制,可以得到一个40位的字符串。
SHA-2算法:
SHA算法家族除了其代表SHA-1算法以外,还有SHA-224、SHA-256、SHA-384和SHA-512四种SHA算法的变体,以其摘要信息字节长度不同而命名,通常将这组算法并称为SHA-2算法。摘要信息字节长度的差异是SHA-2和SHA-1算法的最大差异。
二、应用分析
如果甲乙双方进行明文消息通讯,但要求能够鉴别消息在传输过程中是否被篡改,就可以按照下面所示的模型来进行。当然,此模型对MD和SHA算法同样适用。
三、应用实现:
在java6中。MessageDigest类支持MD算法的同时也支持SHA算法,几乎涵盖了我们所知的全部SHA系列算法,主要包含SHA-1、SHA-256、SHA-384、SHA-512四种算法。通过BouncyCastle组件,可以支持SHA-224算法。
1、Sun的实现的应用
package com.tao.test; import java.security.MessageDigest; import javax.xml.bind.annotation.adapters.HexBinaryAdapter; /** * 工具类 */ class SHACoder { /** * SHA-1消息摘要算法 */ public static String encodeSHA(byte[] data) throws Exception { // 初始化MessageDigest,SHA即SHA-1的简称 MessageDigest md = MessageDigest.getInstance("SHA"); // 执行摘要方法 byte[] digest = md.digest(data); return new HexBinaryAdapter().marshal(digest); } /** * SHA-256消息摘要算法 */ public static String encodeSHA256(byte[] data) throws Exception { // 初始化MessageDigest,SHA即SHA-1的简称 MessageDigest md = MessageDigest.getInstance("SHA-256"); // 执行摘要方法 byte[] digest = md.digest(data); return new HexBinaryAdapter().marshal(digest); } /** * SHA-384消息摘要算法 */ public static String encodeSHA384(byte[] data) throws Exception { // 初始化MessageDigest,SHA即SHA-1的简称 MessageDigest md = MessageDigest.getInstance("SHA-384"); // 执行摘要方法 byte[] digest = md.digest(data); return new HexBinaryAdapter().marshal(digest); } /** * SHA-512消息摘要算法 */ public static String encodeSHA512(byte[] data) throws Exception { // 初始化MessageDigest,SHA即SHA-1的简称 MessageDigest md = MessageDigest.getInstance("SHA-512"); // 执行摘要方法 byte[] digest = md.digest(data); return new HexBinaryAdapter().marshal(digest); } } /** * 测试类 */ public class SHATest { public static void main(String[] args) throws Exception { String testString="asd`12asd31"; System.out.println(SHACoder.encodeSHA(testString.getBytes())); System.out.println(SHACoder.encodeSHA256(testString.getBytes())); System.out.println(SHACoder.encodeSHA384(testString.getBytes())); System.out.println(SHACoder.encodeSHA512(testString.getBytes())); } }
2、BouncyCastle关于SHA-224的实现和应用
package Test; import java.security.MessageDigest; import java.security.Security; import javax.xml.bind.annotation.adapters.HexBinaryAdapter; import org.bouncycastle.jce.provider.BouncyCastleProvider; /** * 工具类 */ class SHACoder { /** * SHA-224消息摘要算法 */ public static String encodeSHA(byte[] data) throws Exception { //加入BouncyCastle的支持 Security.addProvider(new BouncyCastleProvider()); // 初始化MessageDigest,SHA即SHA-1的简称 MessageDigest md = MessageDigest.getInstance("SHA-224"); // 执行摘要方法 byte[] digest = md.digest(data); return new HexBinaryAdapter().marshal(digest); } } /** * 测试类 */ public class SHATest { public static void main(String[] args) throws Exception { String testString="asd`12asd31"; System.out.println(SHACoder.encodeSHA(testString.getBytes())); } }
DigestUtls类除了MD5算法外,还支持多种SHA系列算法,虽然java6也都支持 ,但是它提供了更为方便的方法。
package Test; import java.security.MessageDigest; import javax.xml.bind.annotation.adapters.HexBinaryAdapter; import org.apache.commons.codec.digest.DigestUtils; /** * 工具类 */ class SHACoder { /** * SHA-1消息摘要算法,返回字节数组 */ public static byte[] encodeSHA(byte[] data) throws Exception { return DigestUtils.sha(data); } /** * SHA-1消息摘要算法,返回十六进制字符串 */ public static String encodeSHAHex(byte[] data) throws Exception { return DigestUtils.shaHex(data); } /** * SHA-256消息摘要算法,返回字节数组 */ public static byte[] encodeSHA256(byte[] data) throws Exception { return DigestUtils.sha256(data); } /** * SHA-256消息摘要算法,返回十六进制字符串 */ public static String encodeSHA256Hex(byte[] data) throws Exception { return DigestUtils.sha256Hex(data); } /** * SHA-384消息摘要算法,返回字节数组 */ public static byte[] encodeSHA384(byte[] data) throws Exception { return DigestUtils.sha384(data); } /** * SHA-384消息摘要算法,返回十六进制字符串 */ public static String encodeSHA384Hex(byte[] data) throws Exception { return DigestUtils.sha384Hex(data); } /** * SHA-512消息摘要算法,返回字节数组 */ public static byte[] encodeSHA512(byte[] data) throws Exception { return DigestUtils.sha512(data); } /** * SHA-512消息摘要算法,返回十六进制字符串 */ public static String encodeSHA512Hex(byte[] data) throws Exception { return DigestUtils.sha512Hex(data); } } /** * 测试类 */ public class SHATest { public static void main(String[] args) throws Exception { String testString="asd`12asd31"; System.out.println(SHACoder.encodeSHAHex(testString.getBytes())); System.out.println(SHACoder.encodeSHA256Hex(testString.getBytes())); System.out.println(SHACoder.encodeSHA384Hex(testString.getBytes())); System.out.println(SHACoder.encodeSHA512Hex(testString.getBytes())); } }