diff --git a/src/main/java/net/floodlightcontroller/core/internal/Controller.java b/src/main/java/net/floodlightcontroller/core/internal/Controller.java
index 7f788b1..084d6c4 100644
--- a/src/main/java/net/floodlightcontroller/core/internal/Controller.java
+++ b/src/main/java/net/floodlightcontroller/core/internal/Controller.java
@@ -194,48 +194,6 @@
     // Flag to always flush flow table on switch reconnect (HA or otherwise)
     protected boolean alwaysClearFlowsOnSwAdd = false;
     
-    /*
-    // Storage table names
-    protected static final String CONTROLLER_TABLE_NAME = "controller_controller";
-    protected static final String CONTROLLER_ID = "id";
-    
-    protected static final String SWITCH_TABLE_NAME = "controller_switch";
-    protected static final String SWITCH_DATAPATH_ID = "dpid";
-    protected static final String SWITCH_SOCKET_ADDRESS = "socket_address";
-    protected static final String SWITCH_IP = "ip";
-    protected static final String SWITCH_CONTROLLER_ID = "controller_id";
-    protected static final String SWITCH_ACTIVE = "active";
-    protected static final String SWITCH_CONNECTED_SINCE = "connected_since";
-    protected static final String SWITCH_CAPABILITIES = "capabilities";
-    protected static final String SWITCH_BUFFERS = "buffers";
-    protected static final String SWITCH_TABLES = "tables";
-    protected static final String SWITCH_ACTIONS = "actions";
-
-    protected static final String SWITCH_CONFIG_TABLE_NAME = "controller_switchconfig";
-    protected static final String SWITCH_CONFIG_CORE_SWITCH = "core_switch";
-    
-    protected static final String PORT_TABLE_NAME = "controller_port";
-    protected static final String PORT_ID = "id";
-    protected static final String PORT_SWITCH = "switch_id";
-    protected static final String PORT_NUMBER = "number";
-    protected static final String PORT_HARDWARE_ADDRESS = "hardware_address";
-    protected static final String PORT_NAME = "name";
-    protected static final String PORT_CONFIG = "config";
-    protected static final String PORT_STATE = "state";
-    protected static final String PORT_CURRENT_FEATURES = "current_features";
-    protected static final String PORT_ADVERTISED_FEATURES = "advertised_features";
-    protected static final String PORT_SUPPORTED_FEATURES = "supported_features";
-    protected static final String PORT_PEER_FEATURES = "peer_features";
-    
-    protected static final String CONTROLLER_INTERFACE_TABLE_NAME = "controller_controllerinterface";
-    protected static final String CONTROLLER_INTERFACE_ID = "id";
-    protected static final String CONTROLLER_INTERFACE_CONTROLLER_ID = "controller_id";
-    protected static final String CONTROLLER_INTERFACE_TYPE = "type";
-    protected static final String CONTROLLER_INTERFACE_NUMBER = "number";
-    protected static final String CONTROLLER_INTERFACE_DISCOVERED_IP = "discovered_ip";
-    */
-    
-    
     // Perf. related configuration
     protected static final int SEND_BUFFER_SIZE = 4 * 1024 * 1024;
     protected static final int BATCH_MAX_SIZE = 100;
@@ -583,10 +541,6 @@
                     explanation="Could not parse a message from the switch",
                     recommendation=LogMessageDoc.CHECK_SWITCH),
             @LogMessageDoc(level="ERROR",
-                    message="Terminating controller due to storage exception",
-                    explanation=ERROR_DATABASE,
-                    recommendation=LogMessageDoc.CHECK_CONTROLLER),
-            @LogMessageDoc(level="ERROR",
                     message="Could not process message: queue full",
                     explanation="OpenFlow messages are arriving faster than " +
                                 " the controller can process them.",
@@ -1759,227 +1713,6 @@
     // Initialization
     // **************
 
-    /*
-    protected void updateAllInactiveSwitchInfo() {
-        if (role == Role.SLAVE) {
-            return;
-        }
-        String controllerId = getControllerId();
-        String[] switchColumns = { SWITCH_DATAPATH_ID,
-                                   SWITCH_CONTROLLER_ID,
-                                   SWITCH_ACTIVE };
-        String[] portColumns = { PORT_ID, PORT_SWITCH };
-        IResultSet switchResultSet = null;
-        try {
-            OperatorPredicate op = 
-                    new OperatorPredicate(SWITCH_CONTROLLER_ID,
-                                          OperatorPredicate.Operator.EQ,
-                                          controllerId);
-            switchResultSet = 
-                    storageSource.executeQuery(SWITCH_TABLE_NAME,
-                                               switchColumns,
-                                               op, null);
-            while (switchResultSet.next()) {
-                IResultSet portResultSet = null;
-                try {
-                    String datapathId =
-                            switchResultSet.getString(SWITCH_DATAPATH_ID);
-                    switchResultSet.setBoolean(SWITCH_ACTIVE, Boolean.FALSE);
-                    op = new OperatorPredicate(PORT_SWITCH, 
-                                               OperatorPredicate.Operator.EQ,
-                                               datapathId);
-                    portResultSet = 
-                            storageSource.executeQuery(PORT_TABLE_NAME,
-                                                       portColumns,
-                                                       op, null);
-                    while (portResultSet.next()) {
-                        portResultSet.deleteRow();
-                    }
-                    portResultSet.save();
-                }
-                finally {
-                    if (portResultSet != null)
-                        portResultSet.close();
-                }
-            }
-            switchResultSet.save();
-        }
-        finally {
-            if (switchResultSet != null)
-                switchResultSet.close();
-        }
-    }
-    */
-    
-    /*
-    protected void updateControllerInfo() {
-        updateAllInactiveSwitchInfo();
-        
-        // Write out the controller info to the storage source
-        Map<String, Object> controllerInfo = new HashMap<String, Object>();
-        String id = getControllerId();
-        controllerInfo.put(CONTROLLER_ID, id);
-        storageSource.updateRow(CONTROLLER_TABLE_NAME, controllerInfo);
-    }
-    */
-    
-    /*
-    protected void updateActiveSwitchInfo(IOFSwitch sw) {
-        if (role == Role.SLAVE) {
-            return;
-        }
-        // Obtain the row info for the switch
-        Map<String, Object> switchInfo = new HashMap<String, Object>();
-        String datapathIdString = sw.getStringId();
-        switchInfo.put(SWITCH_DATAPATH_ID, datapathIdString);
-        String controllerId = getControllerId();
-        switchInfo.put(SWITCH_CONTROLLER_ID, controllerId);
-        Date connectedSince = sw.getConnectedSince();
-        switchInfo.put(SWITCH_CONNECTED_SINCE, connectedSince);
-        Channel channel = sw.getChannel();
-        SocketAddress socketAddress = channel.getRemoteAddress();
-        if (socketAddress != null) {
-            String socketAddressString = socketAddress.toString();
-            switchInfo.put(SWITCH_SOCKET_ADDRESS, socketAddressString);
-            if (socketAddress instanceof InetSocketAddress) {
-                InetSocketAddress inetSocketAddress =
-                        (InetSocketAddress)socketAddress;
-                InetAddress inetAddress = inetSocketAddress.getAddress();
-                String ip = inetAddress.getHostAddress();
-                switchInfo.put(SWITCH_IP, ip);
-            }
-        }
-        
-        // Write out the switch features info
-        long capabilities = U32.f(sw.getCapabilities());
-        switchInfo.put(SWITCH_CAPABILITIES, capabilities);
-        long buffers = U32.f(sw.getBuffers());
-        switchInfo.put(SWITCH_BUFFERS, buffers);
-        long tables = U32.f(sw.getTables());
-        switchInfo.put(SWITCH_TABLES, tables);
-        long actions = U32.f(sw.getActions());
-        switchInfo.put(SWITCH_ACTIONS, actions);
-        switchInfo.put(SWITCH_ACTIVE, Boolean.TRUE);
-        
-        // Update the switch
-        storageSource.updateRowAsync(SWITCH_TABLE_NAME, switchInfo);
-        
-        // Update the ports
-        for (OFPhysicalPort port: sw.getPorts()) {
-            updatePortInfo(sw, port);
-        }
-    }
-    */
-    
-    /*
-    protected void updateInactiveSwitchInfo(IOFSwitch sw) {
-        if (role == Role.SLAVE) {
-            return;
-        }
-        log.debug("Update DB with inactiveSW {}", sw);
-        // Update the controller info in the storage source to be inactive
-        Map<String, Object> switchInfo = new HashMap<String, Object>();
-        String datapathIdString = sw.getStringId();
-        switchInfo.put(SWITCH_DATAPATH_ID, datapathIdString);
-        //switchInfo.put(SWITCH_CONNECTED_SINCE, null);
-        switchInfo.put(SWITCH_ACTIVE, Boolean.FALSE);
-        storageSource.updateRowAsync(SWITCH_TABLE_NAME, switchInfo);
-    }
-    */
-
-    /*
-    protected void updatePortInfo(IOFSwitch sw, OFPhysicalPort port) {
-        if (role == Role.SLAVE) {
-            return;
-        }
-        String datapathIdString = sw.getStringId();
-        Map<String, Object> portInfo = new HashMap<String, Object>();
-        int portNumber = U16.f(port.getPortNumber());
-        String id = datapathIdString + "|" + portNumber;
-        portInfo.put(PORT_ID, id);
-        portInfo.put(PORT_SWITCH, datapathIdString);
-        portInfo.put(PORT_NUMBER, portNumber);
-        byte[] hardwareAddress = port.getHardwareAddress();
-        String hardwareAddressString = HexString.toHexString(hardwareAddress);
-        portInfo.put(PORT_HARDWARE_ADDRESS, hardwareAddressString);
-        String name = port.getName();
-        portInfo.put(PORT_NAME, name);
-        long config = U32.f(port.getConfig());
-        portInfo.put(PORT_CONFIG, config);
-        long state = U32.f(port.getState());
-        portInfo.put(PORT_STATE, state);
-        long currentFeatures = U32.f(port.getCurrentFeatures());
-        portInfo.put(PORT_CURRENT_FEATURES, currentFeatures);
-        long advertisedFeatures = U32.f(port.getAdvertisedFeatures());
-        portInfo.put(PORT_ADVERTISED_FEATURES, advertisedFeatures);
-        long supportedFeatures = U32.f(port.getSupportedFeatures());
-        portInfo.put(PORT_SUPPORTED_FEATURES, supportedFeatures);
-        long peerFeatures = U32.f(port.getPeerFeatures());
-        portInfo.put(PORT_PEER_FEATURES, peerFeatures);
-        storageSource.updateRowAsync(PORT_TABLE_NAME, portInfo);
-    }
-    */
-    
-    /**
-     * Read switch port data from storage and write it into a switch object
-     * @param sw the switch to update
-     */
-    /*
-    protected void readSwitchPortStateFromStorage(OFSwitchImpl sw) {
-        OperatorPredicate op = 
-                new OperatorPredicate(PORT_SWITCH, 
-                                      OperatorPredicate.Operator.EQ,
-                                      sw.getStringId());
-        IResultSet portResultSet = 
-                storageSource.executeQuery(PORT_TABLE_NAME,
-                                           null, op, null);
-        //Map<Short, OFPhysicalPort> oldports = 
-        //        new HashMap<Short, OFPhysicalPort>();
-        //oldports.putAll(sw.getPorts());
-
-        while (portResultSet.next()) {
-            try {
-                OFPhysicalPort p = new OFPhysicalPort();
-                p.setPortNumber((short)portResultSet.getInt(PORT_NUMBER));
-                p.setName(portResultSet.getString(PORT_NAME));
-                p.setConfig((int)portResultSet.getLong(PORT_CONFIG));
-                p.setState((int)portResultSet.getLong(PORT_STATE));
-                String portMac = portResultSet.getString(PORT_HARDWARE_ADDRESS);
-                p.setHardwareAddress(HexString.fromHexString(portMac));
-                p.setCurrentFeatures((int)portResultSet.
-                                     getLong(PORT_CURRENT_FEATURES));
-                p.setAdvertisedFeatures((int)portResultSet.
-                                        getLong(PORT_ADVERTISED_FEATURES));
-                p.setSupportedFeatures((int)portResultSet.
-                                       getLong(PORT_SUPPORTED_FEATURES));
-                p.setPeerFeatures((int)portResultSet.
-                                  getLong(PORT_PEER_FEATURES));
-                //oldports.remove(Short.valueOf(p.getPortNumber()));
-                sw.setPort(p);
-            } catch (NullPointerException e) {
-                // ignore
-            }
-        }
-        SwitchUpdate update = new SwitchUpdate(sw, SwitchUpdateType.PORTCHANGED);
-        try {
-            this.updates.put(update);
-        } catch (InterruptedException e) {
-            log.error("Failure adding update to queue", e);
-        }
-    }
-    */
-    
-    /*
-    protected void removePortInfo(IOFSwitch sw, short portNumber) {
-        if (role == Role.SLAVE) {
-            return;
-        }
-        String datapathIdString = sw.getStringId();
-        String id = datapathIdString + "|" + portNumber;
-        storageSource.deleteRowAsync(PORT_TABLE_NAME, id);
-    }
-    */
-
     /**
      * Sets the initial role based on properties in the config params.
      * It looks for two different properties.
@@ -2180,7 +1913,6 @@
         this.factory = new BasicFactory();
         this.providerMap = new HashMap<String, List<IInfoProvider>>();
         setConfigParams(configParams);
-        //this.role = getInitialRole(configParams);
         //Set the controller's role to MASTER so it always tries to do role requests.
         this.role = Role.MASTER;
         this.roleChanger = new RoleChanger();
@@ -2199,40 +1931,9 @@
     public void startupComponents() {
     	try {
 			registryService.registerController(controllerId);
-		} catch (RegistryException e2) {
-			log.warn("Registry service error: {}", e2.getMessage());
+		} catch (RegistryException e) {
+			log.warn("Registry service error: {}", e.getMessage());
 		}
-    	
-    	/*
-        // Create the table names we use
-        storageSource.createTable(CONTROLLER_TABLE_NAME, null);
-        storageSource.createTable(SWITCH_TABLE_NAME, null);
-        storageSource.createTable(PORT_TABLE_NAME, null);
-        storageSource.createTable(CONTROLLER_INTERFACE_TABLE_NAME, null);
-        storageSource.createTable(SWITCH_CONFIG_TABLE_NAME, null);
-        storageSource.setTablePrimaryKeyName(CONTROLLER_TABLE_NAME,
-                                             CONTROLLER_ID);
-        storageSource.setTablePrimaryKeyName(SWITCH_TABLE_NAME,
-                                             SWITCH_DATAPATH_ID);
-        storageSource.setTablePrimaryKeyName(PORT_TABLE_NAME, PORT_ID);
-        storageSource.setTablePrimaryKeyName(CONTROLLER_INTERFACE_TABLE_NAME, 
-                                             CONTROLLER_INTERFACE_ID);
-        storageSource.addListener(CONTROLLER_INTERFACE_TABLE_NAME, this);
-        
-        while (true) {
-            try {
-                updateControllerInfo();
-                break;
-            }
-            catch (StorageException e) {
-                log.info("Waiting for storage source");
-                try {
-                    Thread.sleep(1000);
-                } catch (InterruptedException e1) {
-                }
-            }
-        }
-        */
        
         // Add our REST API
         restApi.addRestletRoutable(new CoreWebRoutable());
@@ -2277,71 +1978,6 @@
         this.haListeners.remove(listener);
     }
     
-    
-    /**
-     * Handle changes to the controller nodes IPs and dispatch update. 
-     */
-    /*
-    @SuppressWarnings("unchecked")
-    protected void handleControllerNodeIPChanges() {
-        HashMap<String,String> curControllerNodeIPs = new HashMap<String,String>();
-        HashMap<String,String> addedControllerNodeIPs = new HashMap<String,String>();
-        HashMap<String,String> removedControllerNodeIPs =new HashMap<String,String>();
-        String[] colNames = { CONTROLLER_INTERFACE_CONTROLLER_ID, 
-                           CONTROLLER_INTERFACE_TYPE, 
-                           CONTROLLER_INTERFACE_NUMBER, 
-                           CONTROLLER_INTERFACE_DISCOVERED_IP };
-        synchronized(controllerNodeIPsCache) {
-            // We currently assume that interface Ethernet0 is the relevant
-            // controller interface. Might change.
-            // We could (should?) implement this using 
-            // predicates, but creating the individual and compound predicate
-            // seems more overhead then just checking every row. Particularly, 
-            // since the number of rows is small and changes infrequent
-            IResultSet res = storageSource.executeQuery(CONTROLLER_INTERFACE_TABLE_NAME,
-                    colNames,null, null);
-            while (res.next()) {
-                if (res.getString(CONTROLLER_INTERFACE_TYPE).equals("Ethernet") &&
-                        res.getInt(CONTROLLER_INTERFACE_NUMBER) == 0) {
-                    String controllerID = res.getString(CONTROLLER_INTERFACE_CONTROLLER_ID);
-                    String discoveredIP = res.getString(CONTROLLER_INTERFACE_DISCOVERED_IP);
-                    String curIP = controllerNodeIPsCache.get(controllerID);
-                    
-                    curControllerNodeIPs.put(controllerID, discoveredIP);
-                    if (curIP == null) {
-                        // new controller node IP
-                        addedControllerNodeIPs.put(controllerID, discoveredIP);
-                    } 
-                    else if (!curIP.equals(discoveredIP)) {
-                        // IP changed                    
-                        removedControllerNodeIPs.put(controllerID, curIP);
-                        addedControllerNodeIPs.put(controllerID, discoveredIP);
-                    }
-                }
-            }
-            // Now figure out if rows have been deleted. We can't use the
-            // rowKeys from rowsDeleted directly, since the tables primary
-            // key is a compound that we can't disassemble
-            Set<String> curEntries = curControllerNodeIPs.keySet();
-            Set<String> removedEntries = controllerNodeIPsCache.keySet();
-            removedEntries.removeAll(curEntries);
-            for (String removedControllerID : removedEntries)
-                removedControllerNodeIPs.put(removedControllerID, controllerNodeIPsCache.get(removedControllerID));
-            controllerNodeIPsCache = (HashMap<String, String>) curControllerNodeIPs.clone();
-            HAControllerNodeIPUpdate update = new HAControllerNodeIPUpdate(
-                                curControllerNodeIPs, addedControllerNodeIPs,
-                                removedControllerNodeIPs);
-            if (!removedControllerNodeIPs.isEmpty() || !addedControllerNodeIPs.isEmpty()) {
-                try {
-                    this.updates.put(update);
-                } catch (InterruptedException e) {
-                    log.error("Failure adding update to queue", e);
-                }
-            }
-        }
-    }
-    */
-    
     @Override
     public Map<String, String> getControllerNodeIPs() {
         // We return a copy of the mapping so we can guarantee that
@@ -2354,23 +1990,6 @@
         return retval;
     }
 
-    /*
-    @Override
-    public void rowsModified(String tableName, Set<Object> rowKeys) {
-        if (tableName.equals(CONTROLLER_INTERFACE_TABLE_NAME)) {
-            handleControllerNodeIPChanges();
-        }
-        
-    }
-
-    @Override
-    public void rowsDeleted(String tableName, Set<Object> rowKeys) {
-        if (tableName.equals(CONTROLLER_INTERFACE_TABLE_NAME)) {
-            handleControllerNodeIPChanges();
-        }
-    }
-    */
-
     @Override
     public long getSystemStartTime() {
         return (this.systemStartTime);
