Message digest algorithm-MAC

1. Brief introduction

Mac (Message Authentication Code, Message Authentication Code) is a hash function algorithm with key. It is compatible with the characteristics of MD and SHA algorithms, and adds key on this basis. Therefore, MAC algorithm is often called HMAC algorithm. Note that the digest value obtained by the MAC algorithm can also be expressed by hexadecimal coding. The digest length of the MAC algorithm is the same as that of the implementation algorithm. For example, the digest length obtained by HmacSHA algorithm is the digest length obtained by SHA1 algorithm, which is 160-bit binary number, converted into hexadecimal code of 40 bits.

2. Model Analysis

Data exchange between Party A and Party B can adopt the following procedures:

(1) Publishing the digest algorithm to Party B (that is, specifying the name of the digest algorithm to be used)

(2) Party A and Party B construct the key according to the agreement, and both parties have the same key (generally, one party notifies the other party after constructing the key, this process does not need to be realized by program, that is, the two parties agree on a string, but this string is not arbitrarily set, but also obtained through related algorithms)

(3) Party A uses the key to digest the message, and then sends (2) the generated key and the generated digest message to Party B together.

(4) After Party B receives the message, it uses the digest algorithm that Party A has published and the agreed key to digest the received message. Then compare their summary message with the summary message sent by Party A. Identify whether the message was sent by Party A.

3. Realization

import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;

import javax.crypto.KeyGenerator;
import javax.crypto.Mac;
import javax.crypto.SecretKey;
import javax.crypto.spec.SecretKeySpec;

/**
 * sun Self-contained
 */
public class MACCoder1 {

	/**
	 * Initialize the key of HmacMD5 
	 * @return byte[] secret key
	 */
	public static byte[] initHmacMD5Key(){
		try {
			//1. Initialization of KeyGenerator
			KeyGenerator keyGenerator = KeyGenerator.getInstance("HmacMD5");
			//2. Generating key
			SecretKey secretKey = keyGenerator.generateKey();
			//3. Acquiring Key
			byte[] b = secretKey.getEncoded();
			return b;
		} catch (NoSuchAlgorithmException e) {
			e.printStackTrace();
		}
		return null;
	}
	
	/** 
     * HmacMD5 Message summary 
     * @param data Data to be digested 
     * @param key secret key 
     * @return byte[] Message summary 
     * */ 
	public static byte[] encodeHmacMD5(byte[] data, byte[] key){		
		try {
			//Restore the key, because the key is owned as byte by the messaging algorithm  
			SecretKey secretKey = new SecretKeySpec(key, "HmacMD5");
			//Instantiate mac
			Mac mac = Mac.getInstance(secretKey.getAlgorithm());
			//Initialize Mac key 
	        mac.init(secretKey);  
	        //Execute message digest processing  
	        return mac.doFinal(data); 
		} catch (NoSuchAlgorithmException e){
			e.printStackTrace();
		} catch (InvalidKeyException e) {
			e.printStackTrace();
		}  
		return null;
	}
	
	public static void main(String[] args) throws Exception {
		String source = "mac test";
		byte[] key = initHmacMD5Key();
		byte[] ss = encodeHmacMD5(source.getBytes("utf-8"),key);
		System.out.println("md5 Generated key:" + key);
		System.out.println("md5 Encrypted messages:" + bytes2HexString(ss));
		
		System.out.println("-------------------------------------");
		key = initHmacSHA256Key();
		ss = encodeHmacSHA256(source.getBytes("utf-8"), key);
		System.out.println("SHA256 Generated key:" + key);
		System.out.println("SHA256 Encrypted messages:" + bytes2HexString(ss));
		
		/***Console Result
		 *  md5 Generated key:[B@73995d80]
			md5 Encrypted message: 02B0744A0BDAAD671324BE6BB411A31C
			-------------------------------------
			SHA256 Generated key:[B@33bfc93a
			SHA256 Encrypted message: 41AC24A928A9CFF77670FC8020DCA73ED7352364DA939162B0DFCCE6A4ECCB89
		 */
	}
	
	/**
     *Converting byte arrays to hexadecimal form 
     * @param b
     * @return
     */
     public static String bytes2HexString(byte[] b) {
        String ret = "";
        for (int i = 0; i < b.length; i++) {
             String hex = Integer.toHexString(b[ i ] & 0xFF);
             if (hex.length() == 1) {
                hex = '0' + hex;
             }
             ret += hex.toUpperCase();
        }
        return ret;
    }
     
     /**
 	 * Initialize the key of HmacSHA256 
 	 * @return byte[] secret key
 	 */
 	public static byte[] initHmacSHA256Key(){
 		try {
 			//1. Initialization of KeyGenerator
 			KeyGenerator keyGenerator = KeyGenerator.getInstance("HmacSHA256");
 			//2. Generating key
 			SecretKey secretKey = keyGenerator.generateKey();
 			//3. Acquiring Key
 			byte[] b = secretKey.getEncoded();
 			return b;
 		} catch (NoSuchAlgorithmException e) {
 			e.printStackTrace();
 		}
 		return null;
 	} 
 	
 	/** 
     * HmacSHA256 Message summary 
     * @param data Data to be digested 
     * @param key secret key 
     * @return byte[] Message summary 
     * */ 
	public static byte[] encodeHmacSHA256(byte[] data, byte[] key){		
		try {
			//Restore the key, because the key is owned as byte by the messaging algorithm  
			SecretKey secretKey = new SecretKeySpec(key, "HmacSHA256");
			//Instantiate mac
			Mac mac = Mac.getInstance(secretKey.getAlgorithm());
			//Initialize Mac key 
	        mac.init(secretKey);  
	        //Execute message digest processing  
	        return mac.doFinal(data); 
		} catch (NoSuchAlgorithmException e){
			e.printStackTrace();
		} catch (InvalidKeyException e) {
			e.printStackTrace();
		}  
		return null;
	}
}

4. Summary

(1) sun supports the algorithm in 5, but does not support conversion to hexadecimal, but it can be assisted by commons codec or bouncycastle's hexadecimal conversion.

(2) bouncycastle supports three complementary algorithms and supports hexadecimal conversion.

Keywords: Mac Java SHA1 codec

Added by akreation on Fri, 07 Jun 2019 03:08:02 +0300