2016-03-31 2 views
1

J'essaye d'avoir le secret (chaîne) dans l'application, n'importe où, sauf pour être! Donc je suis venu avec cette idée d'utiliser le keyStore pour stocker la clé et l'utiliser uniquement pour le cryptage et le décryptage de mon secret. Voici comment je sauve (Crypter) mon secret:Android KeyStore pour stocker le SecretKey pour le cryptage/décryptage

 public static boolean setKeyStoreString(String strToStore, Context context) { 

      if (strToStore == null) return false; 
      if (strToStore.length() == 0) return false; 
      Log.e(TAG, strToStore); 
      try { 
       KeyStore keyStore = KeyStore.getInstance("AndroidKeyStore"); 
       keyStore.load(null); 
       int nBefore = keyStore.size(); 
       // Create the keys if necessary 
       if (!keyStore.containsAlias("phrase")) { 
        KeyGenerator generator = KeyGenerator.getInstance(
          KeyProperties.KEY_ALGORITHM_AES, "AndroidKeyStore"); 
        KeyGenParameterSpec spec = new KeyGenParameterSpec.Builder("phrase", KeyProperties.PURPOSE_ENCRYPT | KeyProperties.PURPOSE_DECRYPT) 
          .setKeySize(256) 
          .setBlockModes(KeyProperties.BLOCK_MODE_CBC) 
          .setUserAuthenticationValidityDurationSeconds(-1) 
          .setRandomizedEncryptionRequired(false) 
          .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_PKCS7) 
          .setUserAuthenticationRequired(false) 
          .build(); 
        generator.init(spec); 
        generator.generateKey(); 
       } 
       int nAfter = keyStore.size(); 
       Log.v(TAG, "Before = " + nBefore + " After = " + nAfter); 


       String filesDirectory = context.getFilesDir().getAbsolutePath(); 
       String encryptedDataFilePath = filesDirectory + File.separator + "my_phrase"; 
    //   Log.v(TAG, "strPhrase = " + strToStore); 
    //   Log.v(TAG, "dataDirectory = " + dataDirectory); 
    //   Log.v(TAG, "filesDirectory = " + filesDirectory); 
    //   Log.v(TAG, "encryptedDataFilePath = " + encryptedDataFilePath); 

       SecretKey secret = (SecretKey) keyStore.getKey("phrase", null); 
       Cipher inCipher = Cipher.getInstance("AES/CBC/PKCS7Padding"); 
       inCipher.init(Cipher.ENCRYPT_MODE, secret); 
       CipherOutputStream cipherOutputStream = new CipherOutputStream(
         new FileOutputStream(encryptedDataFilePath), inCipher); 
       byte[] bytesToStore = strToStore.getBytes("UTF-8"); 

       cipherOutputStream.write(bytesToStore); 
       try { 
        cipherOutputStream.close(); 
       } catch (Exception ex) { 
        ex.printStackTrace(); 
       } 
       return true; 
      } catch (Exception e) { 
       Log.e(TAG, Log.getStackTraceString(e)); 
      } 
      return false; 
     } 

et voici comment je tente de le récupérer:

public static String getKeyStoreString(final Context context) { 

     KeyStore keyStore; 
     String recoveredSecret = ""; 
     String filesDirectory = context.getFilesDir().getAbsolutePath(); 
     String encryptedDataFilePath = filesDirectory + File.separator + "my_phrase"; 
     try { 
      keyStore = KeyStore.getInstance("AndroidKeyStore"); 
      keyStore.load(null); 
      SecretKey secretKey = (SecretKey) 
        keyStore.getKey("phrase", null); 
      if (secretKey == null) throw new RuntimeException("secretKey is null"); 

      Cipher outCipher; 
      outCipher = Cipher.getInstance("AES/CBC/PKCS7Padding"); 
      outCipher.init(Cipher.DECRYPT_MODE, secretKey, new IvParameterSpec(
        new byte[outCipher.getBlockSize()])); 

      CipherInputStream cipherInputStream = new CipherInputStream(
        new FileInputStream(encryptedDataFilePath), outCipher); 
      byte[] roundTrippedBytes = new byte[1000]; //TODO: dynamically resize as we get more data 
      int index = 0; 
      int nextByte; 
      while ((nextByte = cipherInputStream.read()) != -1) { 
       roundTrippedBytes[index] = (byte) nextByte; 
       index++; 
      } 
      recoveredSecret = new String(roundTrippedBytes, 0, index, "UTF-8"); 
      Log.e(TAG, "round tripped string = " + recoveredSecret); 
     } catch (Exception e) { 
      e.printStackTrace(); 
     } 

     Log.e(TAG, "recovered: " + recoveredSecret); 
     return recoveredSecret; 
    } 

le problème est - le résultat est un peu endommagé au début,

-à-dire: un texte frais pour l'extraction >>>>> kX & ALqM, un texte pour l'extraction

Répondre

1

j'ai le même problème je l'ai utilisé Base64.encode(your byte[], Base64.DEFAULT); pour encoder et de décoder Base64.decode(your byte[], Base64.DEFAULT)

essayer de mettre byte[] encode = Base64.encode(bytesToStore, Base64.DEFAULT) après byte[] bytesToStore = strToStore.getBytes("UTF-8"); dans le setKeyStoreString booléenne public static() et vérifier dans le journal

« encode »