java - file encrypt in python decrypt in android -
i have been trying decrypt file in android, encrypted python, here python code used in decrypting.
import os, random, struct crypto.cipher import aes import sys import hashlib print("trying") def encrypt_file(key, in_filename, out_filename=none, chunksize=64*1024): """ encrypts file using aes (cbc mode) given key. key: encryption key - string must either 16, 24 or 32 bytes long. longer keys more secure. in_filename: name of input file out_filename: if none, '<in_filename>.enc' used. chunksize: sets size of chunk function uses read , encrypt file. larger chunk sizes can faster files , machines. chunksize must divisible 16. """ if not out_filename: out_filename = in_filename + '.mjt' iv = 16 * '\x00' encryptor = aes.new(key, aes.mode_cbc, iv) filesize = os.path.getsize(in_filename) open(in_filename, 'rb') infile: open(out_filename, 'wb') outfile: outfile.write(struct.pack('<q', filesize)) # outfile.write(iv) outfile.write(bytes(iv, 'utf-8')) while true: chunk = infile.read(chunksize) if len(chunk) == 0: break elif len(chunk) % 16 != 0: chunk += b' ' * (16 - len(chunk) % 16) outfile.write(encryptor.encrypt(chunk)) # outfile.write(bytes(encryptor.encrypt(chunk), 'utf-8')) def main(): filename1 = sys.argv[-2] filename2 = sys.argv[-1] key = '0123456789abcdef' encrypt_file(key, filename1, filename2) print("done") if __name__ == '__main__': main() and here android function trying decrypt with
private static byte[] ivbytes = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; public static void decrypt(string inputfile, string outputfile, string password) throws ioexception, nosuchalgorithmexception, nosuchpaddingexception, invalidkeyexception, invalidalgorithmparameterexception { fileinputstream fis = new fileinputstream(inputfile); fileoutputstream fos = new fileoutputstream(outputfile); ivparameterspec iv = new ivparameterspec(ivbytes); secretkeyspec sks = new secretkeyspec(password.getbytes(), "aes"); cipher cipher = cipher.getinstance("aes/cbc/nopadding"); cipher.init(cipher.decrypt_mode, sks, iv); cipherinputstream cis = new cipherinputstream(fis, cipher); int b; byte[] d = new byte[1024]; while((b = cis.read(d)) != -1) { fos.write(d, 0, b); } fos.flush(); fos.close(); cis.close(); } this gives while using aes/cbc/nopadding java.io.ioexception: data not block size aligned , when aes/cbc/pkcs5padding used, gives java.io.ioexception: last block incomplete in decryption
aes block cipher messages need padded multiple of block size, both @ encryption , decryption. encryption fine. reads filesize, writes first 8 bytes of file, writes 16 bytes iv , content of file chunk chunk ensuring padding. however, decryption not follow same pattern decryption. aes 128 bit block cipher don't have worry specifying pkcs5padding, need follow same routine in reverse encryption. there bug in code related iv too.
try following , should work:
private static byte[] filesize = new byte[8]; private static byte[] ivbytes = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; public static void decrypt(string inputfile, string outputfile, string password) throws ioexception, nosuchalgorithmexception, nosuchpaddingexception, invalidkeyexception, invalidalgorithmparameterexception { fileinputstream fis = new fileinputstream(inputfile); fileoutputstream fos = new fileoutputstream(outputfile); fis.read(filesize, 0, 8); system.out.println(new string(filesize)); fis.mark(9); fis.read(ivbytes, 0, 16); system.out.println(new string(ivbytes)); fis.mark(25); ivparameterspec iv = new ivparameterspec(ivbytes); secretkeyspec sks = new secretkeyspec(password.getbytes(), "aes"); cipher cipher = cipher.getinstance("aes/cbc/nopadding"); cipher.init(cipher.decrypt_mode, sks, iv); file file = new file(inputfile); int bytelength = (int) file.length() - 24; system.out.println(integer.tostring(bytelength)); byte[] bytes = new byte[bytelength]; bytelength = fis.read(bytes); system.out.println(integer.tostring(bytelength)); system.out.println(new string(bytes)); inputstream bytesstream = new bytearrayinputstream(bytes); cipherinputstream cis = new cipherinputstream(bytesstream, cipher); int b; byte[] d = new byte[1024]; while((b = cis.read(d)) != -1) { fos.write(d, 0, b); } fos.flush(); fos.close(); cis.close(); }
Comments
Post a Comment