Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/389.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/android/231.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 将硬编码文件解密为字节[]_Java_Android_Encryption - Fatal编程技术网

Java 将硬编码文件解密为字节[]

Java 将硬编码文件解密为字节[],java,android,encryption,Java,Android,Encryption,这实际上是一个两个部分 首先我需要 读取文件的内容 将它们加密到字节[] 将字节[]写入文件或其他文件中 然后#2或#3的结果将进入另一个项目。我想保护我们的PEM/DER钥匙 为了解密,我需要 将加密文件的内容读取为字节[] 将它们解密为字节[] 将解密的数据写入文件或使用它代替文件 现在,我有一些基本的密码 KeyGenerator keyGenerator = KeyGenerator.getInstance("AES"); keyGenerator.init(12

这实际上是一个两个部分

首先我需要

  • 读取文件的内容
  • 将它们加密到
    字节[]
  • 字节[]
    写入文件或其他文件中
  • 然后#2或#3的结果将进入另一个项目。我想保护我们的PEM/DER钥匙

    为了解密,我需要

  • 将加密文件的内容读取为
    字节[]
  • 将它们解密为
    字节[]
  • 将解密的数据写入文件或使用它代替文件
  • 现在,我有一些基本的密码

            KeyGenerator keyGenerator = KeyGenerator.getInstance("AES");
        keyGenerator.init(128); // 192 and 256 bits may not be available
    
        SecretKey secretKey = keyGenerator.generateKey();
    
        Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
    
    
        // By initializing the cipher in CBC mode, an "initialization vector" has been randomly
        // generated. This initialization vector will be necessary to decrypt the encrypted data.
        // It is safe to store the initialization vector in plain text for later use. You can obtain
        // it's bytes by calling iv.getIV().
        cipher.init(Cipher.ENCRYPT_MODE, secretKey);
        IvParameterSpec iv = cipher.getParameters().getParameterSpec(IvParameterSpec.class);
            //      IvParameterSpec iv = new IvParameterSpec(IV); //used for the hardcoded one
    
            byte[] encryptedData = cipher.doFinal(data);
    
    还有解密一个

        cipher.init(Cipher.DECRYPT_MODE, secretKey, iv);
        byte[] decryptedData = cipher.doFinal(encryptedData);
        System.out.println("decrypted: " + new String(decryptedData));
    
    问题是:

    给定一个用例场景,很少加密某些东西,并且会分发要在运行时解密的加密密钥,除了cyphertext之外,我还需要保存什么

    我知道我需要保存IV,但是当我解密的时候,解密不是很好——这让我相信我也需要保存秘密密钥

    有谁能给我一些提示,指点或一般安全提示,以更好的解决方案?如果我需要保存密钥、IV和加密数据,我应该将它们存储在哪里?也许硬编码密钥并将IV存储在加密数据中?也许对IV和密钥都进行硬编码,然后将加密数据存储在文件中

    这与理论上的安全无关,请将其视为您可能给试图偷您钥匙的人带来的最大麻烦和不便。我们都知道我不可能完全隐藏它们

    我非常需要这家伙开始的东西


    但是,如果有更好的方法将安全数据输入PemKeyReader,我洗耳恭听。

    共享密钥和加密内容是两件完全不同的事情

    话虽如此,128位的
    AES
    是比
    3DES
    强得多的加密算法,因此您可以做的是保留
    PKI
    基础设施,以交换
    AES密钥
    ,然后使用它们进行加密和解密

    为什么不
    RSA
    <代码> RSA 需要最小512位,将其视为最强,如果增加更多位,则增加加密和解密所需的时间。p> 因此AES是快速和安全的

    用于从字节[]创建密钥

    public static void main(String[] args) throws Exception
    {
        // Initialise secret key with predefined byte array [] like below. I
        // have used simple string to array method to generate 16 byte array.
        // AES Key must be minimum 16 bytes.
        // Now you can put this byte array some where is .SO file.
        // Generate new Key using this byte []
        // Then you can generate a key using device specific information at
        // first boot up.
        // Use second key to encrypt data and first key to encrypt the second
        // key
        // I Hope it clears all the doubts
        SecretKey key = new SecretKeySpec("ABCDEFGHIJKLMNOP".getBytes(), "AES");
        System.out.println(Arrays.toString(key.getEncoded()));
        // Initialise Cipher with AES Algorithm
        Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
        // Set The Encrypt Mode
        cipher.init(Cipher.ENCRYPT_MODE, key);
        // Encrypt some bytes
        byte[] encrypted = cipher.doFinal("ABCDEFGH".getBytes());
        // Print it to vefiry
        System.out.println(Arrays.toString(encrypted));
    
        // Get The IV
        byte[] iv = cipher.getIV();
        System.out.println(iv.length);
        // Now why storing you can create structure like [16 IV][Encrypted Data]
        // And while decrypting you can read first [16] bytes IV and then
        // decrypt remaining bytes
    
        //byte[] iv = new byte[16];
        // System.arraycopy(encrypted, 0, iv, 0, 16)
        //Copy remaining bytes to decrypt
    
    
        // set cipher to decrypt mode
    
        cipher.init(Cipher.DECRYPT_MODE, key,new IvParameterSpec(iv));
    
        // decrypt it
        byte[] decrypted = cipher.doFinal(encrypted);
        System.out.println(new String(decrypted));
    
    }
    
    现在编写一个算法,该算法将从一些随机数据(如设备名、用户名、随机种子等)生成字节[]

    您可以通过在
    C
    中编写算法并创建
    .SO
    文件并使用
    本机调用获取
    字节[]
    来为算法源代码添加更多保护

    做这些有什么好处

  • 事件如果您的so被黑客攻击,它将需要实时环境来运行create key
  • 即使有人将其弄破,损坏也将受到限制,即1个装置
  • 黑客将不得不在每个设备上重复同样的操作,这是非常不可能做到的

  • 通过阅读Oracle Java教程的和部分,可以更好地解决问题的I/O方面。您可以通过将字节写入
    ByteArrayOutputStream
    ,然后使用
    toByteArray()
    方法将字节作为
    字节[]
    来累积内存中的字节。您考虑过基于密码的加密吗?这意味着将明文密码存储在某处。。。没有,但我在听。理想情况下,我希望使用一个文件对另一个文件进行加密,因为它们是成对的。嗯,我喜欢这样,因为这样可以硬编码一个字节[]。对IV和它旁边的密钥进行硬编码怎么样?这样安全吗?我不是“共享”钥匙;我把它们和生产代码一起分发。这一切都与如何在APK中保证它们的安全有关。如果你在应用程序中分发任何密钥,那么很容易被破解,容易受到攻击,这是不安全的。最好的情况是设备算法,它会根据设备类型、用户名、型号等因素生成密钥,然后将其用于加密。文件也需要进行模糊处理,这样就没有人会轻易知道实现了。那么,你是说硬编码唯一安全的东西是加密的数据?为什么不把所有的东西都放进.SO文件?是的,你可以。但是在java中,由于反编译的原因,用代码传递密钥总是有问题。AES是一种对称算法,它的意思是您应该使用加密的密钥进行解密。所以我建议保留默认密钥加密数据交付应用程序,在第一次启动时将密钥更改为某个随机密钥写入密钥并在某处加密数据。在写入到某个位置之前,始终使用默认应用程序密钥加密密钥。同样,该算法容易受到攻击,但由于设备密钥的更改,损害将受到限制。