Memory leak during automatic merge operations from EGit

Properly dispose of the IMergeContext after we're done merging files so
that it doesn't stay registered against the workspace for notifications
on new file diffs.

Only clear invalidated entries in the EMFModelProvider's cache after
we've tried to access it (the cache's cleanup is done on access so we
might get a hit if we try to find our entry while we could have had a
miss if we took the time to clear beforehand).

Change-Id: Ia3fd49cf1531f02077e00956f6a79e35d24024cb
diff --git a/plugins/org.eclipse.emf.compare.egit/src/org/eclipse/emf/compare/egit/internal/merge/RecursiveModelMerger.java b/plugins/org.eclipse.emf.compare.egit/src/org/eclipse/emf/compare/egit/internal/merge/RecursiveModelMerger.java
index 84c2dc4..a64cc3d 100644
--- a/plugins/org.eclipse.emf.compare.egit/src/org/eclipse/emf/compare/egit/internal/merge/RecursiveModelMerger.java
+++ b/plugins/org.eclipse.emf.compare.egit/src/org/eclipse/emf/compare/egit/internal/merge/RecursiveModelMerger.java
@@ -388,8 +388,9 @@
 
 		private boolean run(IProgressMonitor monitor) throws CorruptObjectException, IOException {
 			SubMonitor progress = SubMonitor.convert(monitor, 1);
+			IMergeContext mergeContext = null;
 			try {
-				final IMergeContext mergeContext = prepareMergeContext();
+				mergeContext = prepareMergeContext();
 				final IStatus status = modelMerger.merge(mergeContext, progress.newChild(1));
 				registerHandledFiles(mergeContext, status);
 			} catch (CoreException e) {
@@ -402,6 +403,10 @@
 				Activator.logError(message, e);
 				merger.cleanUp();
 				return false;
+			} finally {
+				if (mergeContext != null) {
+					mergeContext.dispose();
+				}
 			}
 			return true;
 		}
diff --git a/plugins/org.eclipse.emf.compare.ide.ui/src/org/eclipse/emf/compare/ide/ui/internal/logical/EMFModelProvider.java b/plugins/org.eclipse.emf.compare.ide.ui/src/org/eclipse/emf/compare/ide/ui/internal/logical/EMFModelProvider.java
index d3b5b1f..624a442 100644
--- a/plugins/org.eclipse.emf.compare.ide.ui/src/org/eclipse/emf/compare/ide/ui/internal/logical/EMFModelProvider.java
+++ b/plugins/org.eclipse.emf.compare.ide.ui/src/org/eclipse/emf/compare/ide/ui/internal/logical/EMFModelProvider.java
@@ -266,8 +266,6 @@
 			IProgressMonitor monitor) throws CoreException, InterruptedException {
 		SynchronizationModel syncModel;
 		synchronized(contextToResourceMappingCache) {
-			removeEmptyCacheEntries();
-
 			final Cache<IResource, SynchronizationModel> resourceMappingCache = contextToResourceMappingCache
 					.getUnchecked(context);
 			if (LOGGER.isDebugEnabled()) {
@@ -293,6 +291,8 @@
 			} else if (LOGGER.isDebugEnabled()) {
 				LOGGER.debug("Cache FOUND entry for " + file); //$NON-NLS-1$
 			}
+
+			removeEmptyCacheEntries();
 		}
 		return syncModel;
 	}
@@ -306,6 +306,7 @@
 				.asMap().entrySet().iterator();
 		while (entries.hasNext()) {
 			Map.Entry<ResourceMappingContext, Cache<IResource, SynchronizationModel>> entry = entries.next();
+			entry.getValue().cleanUp();
 			if (entry.getValue().size() == 0) {
 				entries.remove();
 			}