The same, but clearer and less code?

This commit is contained in:
Ciaran Gultnieks 2011-02-16 21:04:02 +00:00
parent 95bca18bd3
commit f5d8419d69

View File

@ -223,123 +223,128 @@ public class RepoXMLHandler extends DefaultHandler {
public static boolean doUpdates(Context ctx, DB db) { public static boolean doUpdates(Context ctx, DB db) {
long startTime = System.currentTimeMillis(); long startTime = System.currentTimeMillis();
boolean success = true; boolean success = false;
db.beginUpdate(); db.beginUpdate();
Vector<DB.Repo> repos = db.getRepos(); try
for (DB.Repo repo : repos) { {
if (repo.inuse) { Vector<DB.Repo> repos = db.getRepos();
for (DB.Repo repo : repos) {
if (repo.inuse) {
try { try {
if (repo.pubkey != null) { if (repo.pubkey != null) {
// This is a signed repo - we download the jar file, // This is a signed repo - we download the jar file,
// check the signature, and extract the index... // check the signature, and extract the index...
Log.d("FDroid", "Getting signed index from " Log.d("FDroid", "Getting signed index from "
+ repo.address); + repo.address);
getRemoteFile(ctx, repo.address + "/index.jar", getRemoteFile(ctx, repo.address + "/index.jar",
"tempindex.jar"); "tempindex.jar");
String jarpath = ctx.getFilesDir() + "/tempindex.jar"; String jarpath = ctx.getFilesDir() + "/tempindex.jar";
JarFile jar = new JarFile(jarpath); JarFile jar = new JarFile(jarpath);
JarEntry je = (JarEntry) jar.getEntry("index.xml"); JarEntry je = (JarEntry) jar.getEntry("index.xml");
File efile = new File(ctx.getFilesDir(), File efile = new File(ctx.getFilesDir(),
"/tempindex.xml"); "/tempindex.xml");
InputStream in = new BufferedInputStream(jar InputStream in = new BufferedInputStream(jar
.getInputStream(je), 8192); .getInputStream(je), 8192);
OutputStream out = new BufferedOutputStream( OutputStream out = new BufferedOutputStream(
new FileOutputStream(efile), 8192); new FileOutputStream(efile), 8192);
byte[] buffer = new byte[8192]; byte[] buffer = new byte[8192];
while (true) { while (true) {
int nBytes = in.read(buffer); int nBytes = in.read(buffer);
if (nBytes <= 0) if (nBytes <= 0)
break; break;
out.write(buffer, 0, nBytes); out.write(buffer, 0, nBytes);
} }
out.flush(); out.flush();
out.close(); out.close();
in.close(); in.close();
java.security.cert.Certificate[] certs = je java.security.cert.Certificate[] certs = je
.getCertificates(); .getCertificates();
jar.close(); jar.close();
if (certs == null) { if (certs == null) {
Log.d("FDroid", "No signature found in index"); Log.d("FDroid", "No signature found in index");
return success = false; return false;
} }
if (certs.length != 1) { if (certs.length != 1) {
Log.d("FDroid", "Expected one signature - found " Log.d("FDroid", "Expected one signature - found "
+ certs.length); + certs.length);
return success = false; return false;
}
byte[] sig = certs[0].getEncoded();
byte[] csig = new byte[sig.length * 2];
for (int j = 0; j < sig.length; j++) {
byte v = sig[j];
int d = (v >> 4) & 0xf;
csig[j * 2] = (byte) (d >= 10 ? ('a' + d - 10)
: ('0' + d));
d = v & 0xf;
csig[j * 2 + 1] = (byte) (d >= 10 ? ('a' + d - 10)
: ('0' + d));
}
String ssig = new String(csig);
if (!ssig.equals(repo.pubkey)) {
Log.d("FDroid", "Index signature mismatch");
return false;
}
} else {
// It's an old-fashioned unsigned repo...
Log.d("FDroid", "Getting unsigned index from "
+ repo.address);
getRemoteFile(ctx, repo.address + "/index.xml",
"tempindex.xml");
} }
byte[] sig = certs[0].getEncoded(); // Process the index...
byte[] csig = new byte[sig.length * 2]; SAXParserFactory spf = SAXParserFactory.newInstance();
for (int j = 0; j < sig.length; j++) { SAXParser sp = spf.newSAXParser();
byte v = sig[j]; XMLReader xr = sp.getXMLReader();
int d = (v >> 4) & 0xf; RepoXMLHandler handler = new RepoXMLHandler(repo.address,
csig[j * 2] = (byte) (d >= 10 ? ('a' + d - 10) db);
: ('0' + d)); xr.setContentHandler(handler);
d = v & 0xf;
csig[j * 2 + 1] = (byte) (d >= 10 ? ('a' + d - 10)
: ('0' + d));
}
String ssig = new String(csig);
if (!ssig.equals(repo.pubkey)) { InputStreamReader isr = new FileReader(new File(ctx
Log.d("FDroid", "Index signature mismatch"); .getFilesDir()
return success = false; + "/tempindex.xml"));
InputSource is = new InputSource(isr);
xr.parse(is);
if (handler.pubkey != null && repo.pubkey == null) {
// We read an unsigned index, but that indicates that
// a signed version is now available...
Log
.d("FDroid",
"Public key found - switching to signed repo for future updates");
repo.pubkey = handler.pubkey;
db.updateRepoByAddress(repo);
} }
} else { } catch (Exception e) {
Log.e("FDroid", "Exception updating from " + repo.address
// It's an old-fashioned unsigned repo... + ":\n" + Log.getStackTraceString(e));
Log.d("FDroid", "Getting unsigned index from " return false;
+ repo.address); } finally {
getRemoteFile(ctx, repo.address + "/index.xml", ctx.deleteFile("tempindex.xml");
"tempindex.xml"); ctx.deleteFile("tempindex.jar");
} }
// Process the index...
SAXParserFactory spf = SAXParserFactory.newInstance();
SAXParser sp = spf.newSAXParser();
XMLReader xr = sp.getXMLReader();
RepoXMLHandler handler = new RepoXMLHandler(repo.address,
db);
xr.setContentHandler(handler);
InputStreamReader isr = new FileReader(new File(ctx
.getFilesDir()
+ "/tempindex.xml"));
InputSource is = new InputSource(isr);
xr.parse(is);
if (handler.pubkey != null && repo.pubkey == null) {
// We read an unsigned index, but that indicates that
// a signed version is now available...
Log
.d("FDroid",
"Public key found - switching to signed repo for future updates");
repo.pubkey = handler.pubkey;
db.updateRepoByAddress(repo);
}
} catch (Exception e) {
Log.e("FDroid", "Exception updating from " + repo.address
+ ":\n" + Log.getStackTraceString(e));
return success = false;
} finally {
ctx.deleteFile("tempindex.xml");
ctx.deleteFile("tempindex.jar");
if (!success)
db.cancelUpdate();
} }
} }
success=true;
db.endUpdate();
Log.d("FDroid", "Update completed in "
+ ((System.currentTimeMillis() - startTime) / 1000)
+ " seconds.");
return true;
} finally {
if(!success)
db.cancelUpdate();
} }
db.endUpdate();
Log.d("FDroid", "Update completed in "
+ ((System.currentTimeMillis() - startTime) / 1000)
+ " seconds.");
return true;
} }
} }