--- a/src/main/java/net/timbusproject/dpes/alternative/kb/PackageUniverseBuilder.java
+++ b/src/main/java/net/timbusproject/dpes/alternative/kb/PackageUniverseBuilder.java
@@ -18,10 +18,10 @@
 
 package net.timbusproject.dpes.alternative.kb;
 
-import java.io.File;
+import java.io.FileInputStream;
 import java.io.FileNotFoundException;
 import java.io.IOException;
-import java.io.StringWriter;
+import java.io.ObjectInputStream;
 import java.util.ArrayList;
 import java.util.List;
 import java.util.SortedMap;
@@ -42,9 +42,7 @@
 import org.apache.commons.cli.Options;
 import org.apache.commons.cli.ParseException;
 import org.apache.commons.io.IOUtils;
-
-import com.thoughtworks.xstream.XStream;
-import com.thoughtworks.xstream.io.xml.DomDriver;
+import org.apache.commons.lang3.time.DurationFormatUtils;
 
 /**
  * @author Rudolf Mayer
@@ -53,32 +51,42 @@
 
     public static final String aptitudeSearchCommand = "aptitude search -F %p \".*\"";
 
-    private static final XStream xStream = new XStream(new DomDriver());
-
     static final Logger logUniverse = Logger.getLogger("PackaUniverseBuilder");
 
-    public static void main(String[] args) throws IOException {
-
-        long startTime = System.currentTimeMillis();
-
-        // search all packages
-        ArrayList<String> allPackageNames = VirtualPackageAlternativeIdentifier.searchPackages(aptitudeSearchCommand);
+    public static void main(String[] args) throws IOException, ClassNotFoundException {
+
+        // this holds all the packages
         SortedMap<String, Package> allPackages = new TreeMap<String, Package>();
-        System.out.println("Found " + allPackageNames.size() + " packages.\n");
 
         Options options = new Options();
-        Option optLoadProviders = new Option("f", "file", true, "Load package information from an XML serialised file");
-        options.addOption(optLoadProviders);
+        options.addOption(new Option("l", "loadPackages", true, "Load package information from a serialised file"));
+        options.addOption(new Option("x", "loadPackagesXML", true,
+                "Load package information from an XML serialised file"));
+        options.addOption(new Option("j", "loadPackagesJSON", true,
+                "Load package information from a JSON serialised file"));
 
         CommandLineParser parser = new BasicParser();
         try {
             CommandLine cmd = parser.parse(options, args);
-            if (cmd.hasOption("file")) { // load the package information from the file
-                String providersFileName = cmd.getOptionValue("file");
+            if (cmd.hasOption("loadPackages")) { // load the package information from the serialised file
+                String providersFileName = cmd.getOptionValue("loadPackages");
                 logUniverse.info("Trying to load package information from XML " + providersFileName);
-                allPackages = (SortedMap<String, Package>) xStream.fromXML(new File(providersFileName));
-                logUniverse.info("\tDone!");
-            }
+                allPackages = (SortedMap<String, Package>) new ObjectInputStream(new FileInputStream(providersFileName)).readObject();
+                logUniverse.info("\tDone, found " + allPackages.size() + " packages.");
+            }
+            if (cmd.hasOption("loadPackagesXML")) { // load the package information from the XML file
+                String providersFileName = cmd.getOptionValue("loadPackagesXML");
+                logUniverse.info("Trying to load package information from XML " + providersFileName);
+                allPackages = (SortedMap<String, Package>) SerialisationUtils.readFromXMLFile(providersFileName);
+                logUniverse.info("\tDone, found " + allPackages.size() + " packages.");
+            }
+            if (cmd.hasOption("loadPackagesJSON")) { // load the package information from the XML file
+                String providersFileName = cmd.getOptionValue("loadPackagesJSON");
+                logUniverse.info("Trying to load package information from JSON " + providersFileName);
+                allPackages = (SortedMap<String, Package>) SerialisationUtils.readFromJSONFile(providersFileName);
+                logUniverse.info("\tDone, found " + allPackages.size() + " packages.");
+            }
+
         } catch (ParseException e) {
             System.err.println("CLI parsing failed.  Reason: " + e.getMessage());
             // automatically generate the help statement
@@ -87,10 +95,18 @@
             return;
         }
 
+        long startTime = System.currentTimeMillis();
+
+        // search all packages
+        ArrayList<String> allPackageNames = VirtualPackageAlternativeIdentifier.searchPackages(aptitudeSearchCommand);
+        logUniverse.info("Found " + allPackageNames.size() + " packages.\n");
+
         if (allPackages == null) {
             allPackages = new TreeMap<String, Package>();
             // allPackages = new HashMap<String, Package>(allPackageNames.size());
         }
+
+        // read missing packages
 
         // query the package information, in parallel manner
         int nrOfProcessors = Runtime.getRuntime().availableProcessors();
@@ -114,6 +130,7 @@
             // }
         }
 
+        // wait for all tasks to finish
         eservice.shutdown();
         try {
             eservice.awaitTermination(Long.MAX_VALUE, TimeUnit.NANOSECONDS);
@@ -121,29 +138,51 @@
             System.out.println(e);
         }
 
-        for (Future<Package> future : futuresList) {
-            Package pkg;
+        // store the results - if there were any
+        if (futuresList.size() > 0) {
+            long endReadingPackagesTime = System.currentTimeMillis();
+            logUniverse.info("Reading packages took "
+                    + DurationFormatUtils.formatDurationHMS(endReadingPackagesTime - startTime));
+
+            for (Future<Package> future : futuresList) {
+                Package pkg;
+                try {
+                    pkg = future.get();
+                    allPackages.put(pkg.getName(), pkg);
+                } catch (InterruptedException e) {
+                    e.printStackTrace();
+                } catch (ExecutionException e) {
+                    e.printStackTrace();
+                }
+            }
+
+            // save results
+            final String fileName = "packageDetails-" + OSIdentifier.getEscapedOSString();
+
+            // object serialisation
+            logUniverse.info("Wrote packages to "
+                    + SerialisationUtils.writeAsBinary(allPackages,
+                            VirtualPackageAlternativeIdentifier.PATH_KNOWDLEDGE_BASE + fileName).getAbsolutePath());
+
+            // save packages as JSON
             try {
-                pkg = future.get();
-                allPackages.put(pkg.getName(), pkg);
-            } catch (InterruptedException e) {
-                e.printStackTrace();
-            } catch (ExecutionException e) {
-                e.printStackTrace();
-            }
-        }
-
-        // save packages in XML
-        final String fileName = "packages-" + OSIdentifier.getEscapedOSString() + ".xml";
-        try {
-            logUniverse.info("Wrote packages to "
-                    + VirtualPackageAlternativeIdentifier.writeAsXML(allPackages, fileName).getAbsolutePath());
-        } catch (FileNotFoundException e1) {
-            // TODO Auto-generated catch block
-            e1.printStackTrace();
-        }
-
-        long endReadingPackagesTime = System.currentTimeMillis();
+                logUniverse.info("Wrote packages to "
+                        + SerialisationUtils.writeAsJSON(allPackages,
+                                VirtualPackageAlternativeIdentifier.PATH_KNOWDLEDGE_BASE, fileName, true).getAbsolutePath());
+            } catch (FileNotFoundException e1) {
+                e1.printStackTrace();
+            }
+
+            // save packages in XML
+            try {
+                logUniverse.info("Wrote packages to "
+                        + SerialisationUtils.writeAsXML(allPackages,
+                                VirtualPackageAlternativeIdentifier.PATH_KNOWDLEDGE_BASE, fileName, true).getAbsolutePath());
+            } catch (FileNotFoundException e1) {
+                e1.printStackTrace();
+            }
+
+        }
 
         // process all packages
 
@@ -182,15 +221,8 @@
 
         long totalEndTime = System.currentTimeMillis();
 
-        logUniverse.info("");
+        logUniverse.info("Total duration: " + DurationFormatUtils.formatDurationHMS(totalEndTime - startTime));
     }
-
-    public static String inputStreamToString(Process process) throws IOException {
-        StringWriter writer = new StringWriter();
-        IOUtils.copy(process.getInputStream(), writer);
-        return writer.toString();
-    }
-
 }
 
 class PackgeDetailsTask implements Callable<Package> {