簡體   English   中英

如何從加密密碼解密密碼

[英]How to decrypt password from encrypted password

當前,我們正在加密用戶從登錄頁面輸入的密碼,並將其存儲在數據庫中。 這里正在開發一個新的登錄頁面以供內部使用,並重復使用相同的用戶名和加密密碼。 如果用戶被授權,則將允許他訪問報告。 在這里,我的問題是,我該如何獲取他們用來加密的密鑰。 想要使用相同的密鑰來解密密碼,那么我可以繼續我的邏輯。

這是我們用來加密密碼的代碼。

user = userRemote.loginUser(userName, new String(EncryptDecrypt.storePassword(password),"Cp1252"));

Here password is Password entered in the login page.

這是加密密碼的方法。

final static byte[] salt = {
        (byte)0xc7, (byte)0x73, (byte)0x21, (byte)0x8c,
        (byte)0x7e, (byte)0xc8, (byte)0xee, (byte)0x99
    };
final static int count = 1;

public static byte[] storePassword(char[] password) throws InternalException {
      PBEKeySpec pbeKeySpec;
      PBEParameterSpec pbeParamSpec;
      SecretKeyFactory keyFac;
      byte[] ciphertext = null;
      try {
        // Install SunJCE provider
        Provider sunJce = new com.sun.crypto.provider.SunJCE();
        Security.addProvider(sunJce);

        // Create PBE parameter set
        pbeParamSpec = new PBEParameterSpec(salt, count);

        pbeKeySpec = new PBEKeySpec(password);
        keyFac = SecretKeyFactory.getInstance("PBEWithMD5AndDES");
        SecretKey pbeKey = keyFac.generateSecret(pbeKeySpec);
        // Create PBE Cipher
        Cipher pbeCipher = Cipher.getInstance("PBEWithMD5AndDES");

        // Initialize PBE Cipher with key and parameters
        pbeCipher.init(Cipher.ENCRYPT_MODE, pbeKey, pbeParamSpec);

        // Our cleartext
        byte[] cleartext = (new String(password)).getBytes("Cp1252");

        // Encrypt the cleartext
        ciphertext = pbeCipher.doFinal(cleartext);
      } catch (BadPaddingException ex) {
        log.error("EncryptDecrypt: " + ex.getMessage());
        throw new InternalException(ex.getMessage());
      } catch (Exception ex) {
        log.error("EncryptDecrypt: " + ex.getMessage());
        throw new InternalException(ex.getMessage());
      }
     return ciphertext;
  }

這是用於解密密碼的類。 在這里,我只有加密的密碼作為解密密碼的輸入。 例如•Ä0?BÒO,因此正在使用它來生成密鑰並對其進行解密。 但是,低於例外。 java.security.spec.InvalidKeySpecException:密碼不是ASCII

import java.security.*;
import javax.crypto.*;
import javax.crypto.spec.*;

public class DecryptPassword {

    public static void main(String[] args) {
        String decryptedStr = checkPassword("•Ä0BÒ¦O");
        System.out.println("decryptedStr : "+decryptedStr);
    }

    final static byte[] salt = {
        (byte)0xc7, (byte)0x73, (byte)0x21, (byte)0x8c,
        (byte)0x7e, (byte)0xc8, (byte)0xee, (byte)0x99
    };

    final static int count = 1;

    static String decryptedPassword = "";

     public static String checkPassword(String encryptedPassword) {
          PBEKeySpec pbeKeySpec;
          PBEParameterSpec pbeParamSpec;
          SecretKeyFactory keyFac;
          try {
            // Install SunJCE provider
            Provider sunJce = new com.sun.crypto.provider.SunJCE();
            Security.addProvider(sunJce);
            // Create PBE parameter set
            pbeParamSpec = new PBEParameterSpec(salt, count);
            pbeKeySpec = new PBEKeySpec(encryptedPassword.toCharArray());
            keyFac = SecretKeyFactory.getInstance("PBEWithMD5AndDES");
            SecretKey pbeKey = keyFac.generateSecret(pbeKeySpec);
            // Create PBE Cipher
            Cipher pbeCipher = Cipher.getInstance("PBEWithMD5AndDES");
            // Initialize PBE Cipher with key and parameters
            pbeCipher.init(Cipher.DECRYPT_MODE, pbeKey, pbeParamSpec);
            byte[] decrypted = pbeCipher.doFinal(encryptedPassword.getBytes());
            decryptedPassword = decrypted.toString();
        } catch (BadPaddingException ex) {
          System.out.println("EncryptDecrypt: " + ex.getMessage());
        } catch (Exception ex) {
          System.out.println("EncryptDecrypt: " + ex.getMessage());
        }
        return decryptedPassword;
      }

}

在這里我應該能夠成功解密密碼,但是不能解密。有人可以幫助我這里缺少什么嗎? 提前致謝。

那不是加密,那是哈希! (輪輞次)

storePassword例程有效地使用密碼對其進行加密; 更確切地說, PBEwithMD5andDES使用原始PKCS5v1派生函數從密碼派生的密鑰(為清楚起見,現在重新命名為PBKDF1),並以MD5,固定鹽和1(!)迭代實例化,以原始DES CBC加密密碼。 這是以前流行的創建加密哈希的方式的變體。

在1960年代和1970年代,也許是1980年代,在密碼學家將注意力轉移到設計特定的密碼哈希函數之前,使密碼成為唯一的密碼基元,將密碼(密鑰排列)轉換為密碼哈希(非密鑰函數)的一種常用方法是將數據用作加密常量的密鑰; 對此的微小變化被實現為一個庫函數,該庫函數不正確地命名為crypt 1970年早期的Unix Unix中用作密碼哈希函數,至今仍記憶猶新(有時甚至使用過),但現在經常使用DES-cryptdescrypt來區別於其他方法自此開發了替代產品。

與旨在被解密的密碼不同,這是一個散列並且被設計為不可逆。 我不知道有什么方法可以比蠻力更容易地扭轉這種方法(即分析性的“斷裂”),但是原始的DES,現在通常稱為單DES(或1DES),以區別於其直接后繼三元DES(或3DES或正式的TDEA)足夠脆弱,如果您真的願意的話,現在可以將其強行使用。 例如, JTR報告單鹽解密的速度大約為10M-30M /秒,相當於簡單DES的速度約為0.5G /秒,因此在一台計算機上嘗試所有DES密鑰將花費數年,而在一千台計算機上則需要數天。 ,或者一百萬台計算機需要幾分鍾的時間。 關於hashcat的數據較難找到,但看起來大致可比。 如果您知道如何選擇密碼,則嘗試僅使用可能的密碼而不是所有可能的密鑰可能會更快。

但是不要。 驗證密碼哈希正確方法是讓用戶提供要求的密碼,使用相同的參數重復哈希過程(此處很簡單,因為它沒有像應有的那樣使用可變的salt),並查看新的哈希結果是否匹配存儲的一個。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM