Skip to content

Commit

Permalink
Close stream in finally block, increase buffer size, detect crx via m…
Browse files Browse the repository at this point in the history
…agic number
  • Loading branch information
agrieve committed Mar 7, 2014
1 parent f73bf18 commit 1510e74
Showing 1 changed file with 34 additions and 20 deletions.
54 changes: 34 additions & 20 deletions src/android/Zip.java
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@

import java.io.BufferedInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.FileNotFoundException;
import java.util.zip.ZipEntry;
Expand All @@ -20,7 +20,7 @@
public class Zip extends CordovaPlugin {

private static final String LOG_TAG = "Zip";

@Override
public boolean execute(String action, CordovaArgs args, final CallbackContext callbackContext) throws JSONException {
if ("unzip".equals(action)) {
Expand All @@ -38,7 +38,17 @@ public void run() {
});
}

// Can't use DataInputStream because it has the wrong endian-ness.
private static int readInt(InputStream is) throws IOException {
int a = is.read();
int b = is.read();
int c = is.read();
int d = is.read();
return a | b << 8 | c << 16 | d << 24;
}

private void unzipSync(CordovaArgs args, CallbackContext callbackContext) {
InputStream inputStream = null;
try {
String zipFileName = args.getString(0);
String outputDirectory = args.getString(1);
Expand All @@ -64,9 +74,12 @@ private void unzipSync(CordovaArgs args, CallbackContext callbackContext) {
throw new FileNotFoundException("File: \"" + outputDirectory + "\" not found");
}

InputStream is = resourceApi.openForRead(zipUri).inputStream;

if (zipFileName.endsWith("crx")) {
inputStream = new BufferedInputStream(resourceApi.openForRead(zipUri).inputStream);
inputStream.mark(10);
int magic = readInt(inputStream);
if (magic != 875721283) { // CRX identifier
inputStream.reset();
} else {
// CRX files contain a header. This header consists of:
// * 4 bytes of magic number
// * 4 bytes of CRX format version,
Expand All @@ -75,28 +88,22 @@ private void unzipSync(CordovaArgs args, CallbackContext callbackContext) {
// * the public key
// * the signature
// and then the ordinary zip data follows. We skip over the header before creating the ZipInputStream.
readInt(inputStream); // version == 2.
int pubkeyLength = readInt(inputStream);
int signatureLength = readInt(inputStream);

is.skip(8); // 4 bytes for the magic number, 4 for the version.
int pubkeyLength = is.read();
pubkeyLength += is.read() << 8;
is.skip(2);

int signatureLength = is.read();
signatureLength += is.read() << 8;
is.skip(2);

is.skip(pubkeyLength + signatureLength);
inputStream.skip(pubkeyLength + signatureLength);
}

// The inputstream is now pointing at the start of the actual zip file content.
ZipInputStream zis = new ZipInputStream(new BufferedInputStream(is));
ZipInputStream zis = new ZipInputStream(inputStream);
inputStream = zis;

ZipEntry ze;

byte[] buffer = new byte[1024];
byte[] buffer = new byte[32 * 1024];
boolean anyEntries = false;

while ((ze = zis.getNextEntry()) != null)
while ((ze = zis.getNextEntry()) != null)
{
anyEntries = true;
String compressedName = ze.getName();
Expand All @@ -108,6 +115,7 @@ private void unzipSync(CordovaArgs args, CallbackContext callbackContext) {
File file = new File(outputDirectory + compressedName);
file.getParentFile().mkdirs();
if(file.exists() || file.createNewFile()){
Log.w("Zip", "extracting: " + file.getPath());
FileOutputStream fout = new FileOutputStream(file);
int count;
while ((count = zis.read(buffer)) != -1)
Expand All @@ -120,7 +128,6 @@ private void unzipSync(CordovaArgs args, CallbackContext callbackContext) {
}
zis.closeEntry();
}
zis.close();
if (anyEntries)
callbackContext.success();
else
Expand All @@ -129,6 +136,13 @@ private void unzipSync(CordovaArgs args, CallbackContext callbackContext) {
String errorMessage = "An error occurred while unzipping.";
callbackContext.error(errorMessage);
Log.e(LOG_TAG, errorMessage, e);
} finally {
if (inputStream != null) {
try {
inputStream.close();
} catch (IOException e) {
}
}
}
}

Expand Down

0 comments on commit 1510e74

Please sign in to comment.