Bug 317726 -  Persistent Cache improvements
diff --git a/org.eclipse.cdt.debug.edc.arm/src/org/eclipse/cdt/debug/edc/internal/arm/ARMStack.java b/org.eclipse.cdt.debug.edc.arm/src/org/eclipse/cdt/debug/edc/internal/arm/ARMStack.java
index 60d3716..f782dd0 100644
--- a/org.eclipse.cdt.debug.edc.arm/src/org/eclipse/cdt/debug/edc/internal/arm/ARMStack.java
+++ b/org.eclipse.cdt.debug.edc.arm/src/org/eclipse/cdt/debug/edc/internal/arm/ARMStack.java
@@ -167,10 +167,9 @@
 				if (reader != null)
 				{
 					// Check the persistent cache
-					Object cachedData = ARMPlugin.getDefault().getCache().getCachedData(cacheKey, reader.getModificationDate());
-					if (cachedData != null && cachedData instanceof Map<?,?>)
+					cachedMapping = ARMPlugin.getDefault().getCache().getCachedData(cacheKey, Map.class, reader.getModificationDate());
+					if (cachedMapping != null)
 					{
-						cachedMapping = (Map<IAddress, IAddress>) cachedData;
 						IAddress cachedAddress = cachedMapping.get(module.toLinkAddress(pcValue));
 						if (cachedAddress != null)
 							functionStartAddress = module.toRuntimeAddress(cachedAddress);	
diff --git a/org.eclipse.cdt.debug.edc.arm/src/org/eclipse/cdt/debug/edc/internal/arm/TargetEnvironmentARM.java b/org.eclipse.cdt.debug.edc.arm/src/org/eclipse/cdt/debug/edc/internal/arm/TargetEnvironmentARM.java
index dc59f21..5e5fe0b 100644
--- a/org.eclipse.cdt.debug.edc.arm/src/org/eclipse/cdt/debug/edc/internal/arm/TargetEnvironmentARM.java
+++ b/org.eclipse.cdt.debug.edc.arm/src/org/eclipse/cdt/debug/edc/internal/arm/TargetEnvironmentARM.java
@@ -184,10 +184,9 @@
 			String cacheKey = reader.getSymbolFile().toOSString() + IS_THUMB_MODE;
 			if (reader != null)
 			{
-				Object cachedData = ARMPlugin.getDefault().getCache().getCachedData(cacheKey, reader.getModificationDate());
-				if (cachedData != null && cachedData instanceof Map<?,?>)
+				cachedValues = ARMPlugin.getDefault().getCache().getCachedData(cacheKey, Map.class, reader.getModificationDate());
+				if (cachedValues != null)
 				{
-					cachedValues = (Map<IAddress, Boolean>) cachedData;
 					Boolean cachedValue = cachedValues.get(linkAddress);
 					if (cachedValue != null)
 						return cachedValue;
diff --git a/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/internal/PersistentCache.java b/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/internal/PersistentCache.java
index bdd0a79..695ad9d 100644
--- a/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/internal/PersistentCache.java
+++ b/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/internal/PersistentCache.java
@@ -13,8 +13,10 @@
 import java.io.File;
 import java.io.FileInputStream;
 import java.io.FileOutputStream;
+import java.io.IOException;
 import java.io.ObjectInputStream;
 import java.io.ObjectOutputStream;
+import java.io.ObjectStreamClass;
 import java.io.Serializable;
 import java.util.Collection;
 import java.util.Collections;
@@ -50,8 +52,12 @@
 			return location;
 		}
 
-		private Object getData() {
-			return data;
+		@SuppressWarnings("unchecked")
+		private <T> T getData(Class<T> expectedClass) {
+			if (expectedClass.isInstance(data))
+				return (T) data;
+			else
+				return null;
 		}
 
 		private long getFreshness() {
@@ -95,7 +101,7 @@
 		return result;		
 	}
 
-	public Object getCachedData(String cacheIdentifier, long freshness) {
+	public <T> T getCachedData(String cacheIdentifier, Class<T> expectedClass, long freshness) {
 	// 	freshness  = 0;
 		CacheEntry cache = caches.get(cacheIdentifier);
 		
@@ -104,10 +110,11 @@
 		
 		if (cache != null)
 		{
-			long cachedFreshness = cache.getFreshness();			
-			if (cachedFreshness == freshness)
+			long cachedFreshness = cache.getFreshness();
+			T result = cache.getData(expectedClass);
+			if (cachedFreshness == freshness && result != null)
 			{
-				return cache.getData();
+				return result;
 			}
 			else
 			{
@@ -120,16 +127,28 @@
 
 	private CacheEntry loadCachedData(IPath location, String cacheIdentifier) {
 		IPath flushPath = location.append(Integer.toString(cacheIdentifier.hashCode())).addFileExtension("txt");
-		
+
 		if (flushPath.toFile().exists())
 		{
 			try {
+				final ClassLoader classLoader = EDCDebugger.getDefault().getClass().getClassLoader();
 				FileInputStream fis = new FileInputStream(flushPath.toFile());
-				ObjectInputStream ois = new ObjectInputStream(fis);
-				return new CacheEntry(ois);
+				ObjectInputStream ois = new ObjectInputStream(fis) {
+
+					@Override
+					protected Class<?> resolveClass(ObjectStreamClass desc)
+					throws IOException, ClassNotFoundException {
+						String name = desc.getName();
+						try {
+							return classLoader.loadClass(name);
+						} catch (ClassNotFoundException e) {
+							return super.resolveClass(desc);
+						}
+					}};
+					return new CacheEntry(ois);
 			} catch (Exception e) {}
 		}
-		
+
 		return null;
 	}
 
diff --git a/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/internal/services/dsf/Modules.java b/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/internal/services/dsf/Modules.java
index 6c4726c..96b535e 100644
--- a/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/internal/services/dsf/Modules.java
+++ b/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/internal/services/dsf/Modules.java
@@ -638,10 +638,10 @@
 				Map<String, Collection<AddressRange>> cachedRanges = new HashMap<String, Collection<AddressRange>>();
 				// Check the persistent cache
 				String cacheKey = reader.getSymbolFile().toOSString() + ADDRESS_RANGE_CACHE;
-				Object cachedData = EDCDebugger.getDefault().getCache().getCachedData(cacheKey, reader.getModificationDate());
-				if (cachedData != null && cachedData instanceof Map<?,?>)
+				Map<String, Collection<AddressRange>> cachedData = EDCDebugger.getDefault().getCache().getCachedData(cacheKey, Map.class, reader.getModificationDate());
+				if (cachedData != null)
 				{
-					cachedRanges = (Map<String, Collection<AddressRange>>) cachedData;
+					cachedRanges = cachedData;
 					linkAddressRanges = cachedRanges.get(file + line);
 				}
 				
diff --git a/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/internal/symbols/dwarf/DwarfDebugInfoProvider.java b/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/internal/symbols/dwarf/DwarfDebugInfoProvider.java
index 8c732aa..afdf9e2 100644
--- a/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/internal/symbols/dwarf/DwarfDebugInfoProvider.java
+++ b/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/internal/symbols/dwarf/DwarfDebugInfoProvider.java
@@ -1088,7 +1088,7 @@
 		if (referencedFiles.isEmpty()) {
 			// Check the persistent cache
 			String cacheKey = getSymbolFile().toOSString() + SOURCE_FILES_CACHE;
-			Object cachedFiles = EDCDebugger.getDefault().getCache().getCachedData(cacheKey, symbolFileLastModified);
+			Set<String> cachedFiles = EDCDebugger.getDefault().getCache().getCachedData(cacheKey, Set.class, symbolFileLastModified);
 			if (cachedFiles == null)
 			{
 				DwarfInfoReader reader = new DwarfInfoReader(this);
@@ -1097,8 +1097,7 @@
 				EDCDebugger.getDefault().getCache().putCachedData(cacheKey, (Serializable) new HashSet<String>(referencedFiles), symbolFileLastModified);
 			}
 			else
-				if (cachedFiles instanceof Set<?>)
-					referencedFiles = (Set<String>) cachedFiles;
+				referencedFiles = (Set<String>) cachedFiles;
 		}
 
 		return referencedFiles.toArray(new String[referencedFiles.size()]);
diff --git a/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/services/Stack.java b/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/services/Stack.java
index 4dbfd2d..ed3bb40 100644
--- a/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/services/Stack.java
+++ b/org.eclipse.cdt.debug.edc/src/org/eclipse/cdt/debug/edc/services/Stack.java
@@ -325,10 +325,10 @@
 						{
 							// Check the persistent cache
 							String cacheKey = reader.getSymbolFile().toOSString() + FRAME_PROPERTY_CACHE;
-							Object cachedData = EDCDebugger.getDefault().getCache().getCachedData(cacheKey, reader.getModificationDate());
-							if (cachedData != null && cachedData instanceof Map<?,?>)
+							Map<IAddress, Map<String, Object>> cachedData = EDCDebugger.getDefault().getCache().getCachedData(cacheKey, Map.class, reader.getModificationDate());
+							if (cachedData != null)
 							{
-								cachedFrameProperties = (Map<IAddress, Map<String, Object>>) cachedData;
+								cachedFrameProperties = cachedData;
 								Map<String, Object> cachedProperties = cachedFrameProperties.get(module.toLinkAddress(ipAddress));
 								if (cachedProperties != null)
 								{