2017-08-04 64 views
0


我正在做一個項目,其中應保證數據傳輸。我正在使用基於密碼的加密與MD5和DES加密文件。
用於加密文件的類:使用套接字傳輸加密文件並使用DES和MD5解密文件

public class FileEncryptor {  
    private static String filename; 
    private static String password; 
    private static FileInputStream inFile; 
    private static FileOutputStream outFile; 
    public static String tempFilename; 
    public static File tempFile; 

    public static File encryptFile(File f, String passkey) throws Exception { 
     if(f.isDirectory()) { 
      JOptionPane.showMessageDialog(null, "file object is a directory"); 
      return null; 
     } 
     filename = f.getPath(); 
     password = passkey;  
     //Need to create a temporary file which is filled with the encrypted data. 
     tempFilename = filename + ".des"; 
     tempFile = new File(tempFilename);  
     inFile = new FileInputStream(f); 
     outFile = new FileOutputStream(tempFile);  
     // Use PBEKeySpec to create a key based on a password. 
     // The password is passed as a character array. 
     PBEKeySpec keySpec = new PBEKeySpec(password.toCharArray()); 
     SecretKeyFactory sKeyFac = SecretKeyFactory.getInstance("PBEWithMD5AndDES"); 
     SecretKey sKey = sKeyFac.generateSecret(keySpec);  
     byte[] salt = new byte[8]; 
     Random rnd = new Random(); 
     rnd.nextBytes(salt); 
     int iterations = 100;  
     //Create the parameter spec for this salt and iteration count 
     PBEParameterSpec parameterSpec = new PBEParameterSpec(salt, iterations); 
     //Create the cipher and initiate it for encryption 
     Cipher c = Cipher.getInstance("PBEWithMD5AndDES"); 
     c.init(Cipher.ENCRYPT_MODE, sKey, parameterSpec); 

     //Need to write the salt into the file. It is required for decryption 
     outFile.write(salt); 

     //Read the file and encrypt its bytes 
     byte[] input = new byte[64]; 
     int bytesRead; 
     while((bytesRead = inFile.read(input)) != -1) { 
      byte[] output = c.update(input, 0, bytesRead); 
      if(output != null) { outFile.write(output); }   
     } 

     byte[] output = c.doFinal(); 
     if(output != null) { outFile.write(output); } 

     //Closing the streams before exiting. 
     inFile.close(); 
     outFile.flush(); 
     outFile.close(); 

     return tempFile; 
    } 

} 

用於解密所述文件中的類:

public class FileDecryptor { 
  
    private static String filename; 
    private static String password; 
    private static FileInputStream inFile; 
    private static FileOutputStream outFile; 

    public static File decryptFile(File encryptedFile, String passkey) throws NoSuchAlgorithmException, 
                  InvalidKeySpecException, IOException, NoSuchPaddingException, 
                  InvalidKeyException, InvalidAlgorithmParameterException, IllegalBlockSizeException, BadPaddingException { 

     String encryptedfilename = encryptedFile.getPath(); 
     password = passkey; 

     inFile = new FileInputStream(encryptedFile); 
     StringBuffer sb = new StringBuffer(encryptedfilename); 
     sb.reverse(); 
     sb.delete(0, 3); 
     sb.reverse();   //removing the ".des" extension of the encrypted file 
     filename = new String(sb) + ".dec"; 

     File decrypFile = new File(filename); 
     outFile = new FileOutputStream(decrypFile); 

     PBEKeySpec keySpec = new PBEKeySpec(password.toCharArray()); 
     SecretKeyFactory sKeyFac = SecretKeyFactory.getInstance("PBEWithMD5AndDES"); 
     SecretKey sKey = sKeyFac.generateSecret(keySpec); 

     // Read in the previously stored salt and set the iteration count. 
     byte[] salt = new byte[8]; 
     inFile.read(salt); 
     int iterations = 100; 

     PBEParameterSpec parameterSpec = new PBEParameterSpec(salt, iterations); 

     //Create the cipher and initialize it for decryption. 
     Cipher c = Cipher.getInstance("PBEWithMD5AndDES"); 
     c.init(Cipher.DECRYPT_MODE, sKey, parameterSpec); 

     byte[] input = new byte[64]; 
     int bytesRead; 
     while((bytesRead = inFile.read(input)) != -1) { 
      byte[] output = c.update(input, 0, bytesRead); 
      if(output != null) { 
       outFile.write(output); 
      } 
     } 

     byte[] output = c.doFinal(); 
     System.out.println("Decrypted the data...."); 
     System.out.println("Wrting the data into file!!"); 
     if(output != null) { 
      outFile.write(output); 
     } 
     System.out.println("Closing the streams"); 
     inFile.close(); 
     outFile.flush(); 
     outFile.close(); 

     return decrypFile;  
    } 
} 

發送邏輯:

public static void main(String[] args) { 
     // TODO Auto-generated method stub 
     Socket cs; 
     OutputStream os; 
     FileInputStream fis; 
     byte[] b = new byte[6022386]; 
     File f = new File("D:\\abc.txt"); 
     File tempFile; 

     try { 
      tempFile = FileEncryptor.encryptFile(f, "impetus"); 
      fis = new FileInputStream(tempFile); 
      ServerSocket ss = new ServerSocket(7007); 
      System.out.println("Created and listening..."); 
      while(true) { 
       System.out.println("Incoming connection!!!!!!!!"); 
       cs = ss.accept(); 
       System.out.println("Client connected"); 
       os = cs.getOutputStream(); 
       fis.read(b); 
       System.out.println("Sending the encrypted data"); 
       os.write(b); 
      } 
     } catch (Exception e) { 
      e.printStackTrace(); 
     } 
    } 

接收邏輯:

public static void main(String[] args) { 
     // TODO Auto-generated method stub 
     File f = new File("D:\\P2PFolder\\ToDec.txt.des"); 
     FileOutputStream fos; 
     InputStream is; 
     Socket s; 
     int bytesRead = 0; 
     int current = 0; 
     byte[] rb = new byte[6022386]; 
     try { 
      fos = new FileOutputStream(f); 
      System.out.println("Connecting....."); 
      s = new Socket(InetAddress.getLocalHost(), 7007); 
      System.out.println("Connected!!!"); 
      is = s.getInputStream(); 
      do { 
       System.out.println("Reading encrypted data from socket"); 
       bytesRead = is.read(rb, current, (rb.length - current)); 
       System.out.println(new String(rb) + bytesRead); 
       if(bytesRead > 0) { 
        current += bytesRead; 
       } 
      } while(bytesRead > -1); 
      fos.write(rb); 
      is.close(); 
      fos.flush(); 
      fos.close(); 
      System.out.println("Decrypting the file"); 
      FileDecryptor.decryptFile(f, "impetus"); 
     } catch (Exception e) { 
      e.printStackTrace(); 
     } 
    } 

沒有異常被拋出,但也沒有數據正在傳輸。加密部分已成功完成。但傳輸和解密不會發生。我檢查了沒有加密的文件傳輸代碼,它正在工作。加密和解密類別在單獨使用而沒有文件傳輸的情況下也可以工作。有人可以指出我在哪裏錯了嗎?我很抱歉,如果代碼太長,但必須提供我所嘗試的。

+3

啓動調試器,你會立即明智的。 – Kayaman

+1

您是在70年代,80年代還是90年代與某人溝通?由於DES和MD5已被棄用*很久以前*。您應該重新獲得流處理測試。有時你需要一個循環並關閉流(try-with-resources)也是推薦的。 –

+0

@MaartenBodewes haha​​ha對不起,但它是我的大學項目。 –

回答

1
  1. 你是不是在服務器關閉os,所以客戶端複製循環永遠不會終止。

  2. 當你解決這個問題時,你會發現文件太大。

    fis.read(b); 
    System.out.println("Sending the encrypted data"); 
    os.write(b); 
    

的問題是,你的兩個不同的複製過程都是錯誤的。使用Java複製流的規範方法如下:

byte[] buffer = new byte[8192]; // or more 
int count; 
while ((count = in.read(buffer)) > 0) 
{ 
    out.write(buffer, 0, count); 
} 

在兩端都使用它。你不需要一個文件大小的緩衝區,或者更大。

+0

非常感謝你,希望它有幫助 –