Bug 545788 - [metatype] provide caching of metatype information

Change-Id: If76fa973a32f1dedded57211370c64bd5d81c7cf
Signed-off-by: Thomas Watson <tjwatson@us.ibm.com>
diff --git a/bundles/org.eclipse.equinox.compendium.tests/bundles_src/metatype/tb9/OSGI-INF/metatype/metadata.xml b/bundles/org.eclipse.equinox.compendium.tests/bundles_src/metatype/tb9/OSGI-INF/metatype/metadata.xml
index eb86ab3..6e45c1a 100644
--- a/bundles/org.eclipse.equinox.compendium.tests/bundles_src/metatype/tb9/OSGI-INF/metatype/metadata.xml
+++ b/bundles/org.eclipse.equinox.compendium.tests/bundles_src/metatype/tb9/OSGI-INF/metatype/metadata.xml
@@ -5,9 +5,9 @@
 		xsi:schemaLocation="http://www.org.osgi/xmlns/metatype/v1.2.0/md metatype.xsd">
 	<OCD id="1" name="ocd1">
 		<AD name="ad1" id="1" type="String"/>
-		<Icon size="10000" resource="icons/tn_ibm_turns_100-100x100.jpg"/>
-		<Icon size="22500" resource="icons/tn_ibm_turns_100-150x150.jpg"/>
-		<Icon size="40000" resource="icons/tn_ibm_turns_100-200x200.jpg"/>
+		<Icon size="4931" resource="icons/tn_ibm_turns_100-100x100.jpg"/>
+		<Icon size="7933" resource="icons/tn_ibm_turns_100-150x150.jpg"/>
+		<Icon size="10182" resource="icons/tn_ibm_turns_100-200x200.jpg"/>
 	</OCD>
 	<OCD id="2" name="ocd2">
 		<AD id="1" name="ad1" type="Byte"/>
diff --git a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/AbstractTest.java b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/AbstractTest.java
index 406d336..8c03584 100644
--- a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/AbstractTest.java
+++ b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/AbstractTest.java
@@ -17,8 +17,6 @@
 import static org.junit.Assert.fail;
 
 import java.io.*;
-import javax.swing.Icon;
-import javax.swing.ImageIcon;
 import org.eclipse.equinox.compendium.tests.Activator;
 import org.eclipse.equinox.metatype.EquinoxMetaTypeService;
 import org.eclipse.osgi.tests.bundles.BundleInstaller;
@@ -72,8 +70,7 @@
 			} finally {
 				icon.close();
 			}
-			Icon i = new ImageIcon(baos.toByteArray());
-			Assert.assertEquals("Wrong icon size", size, i.getIconHeight() * i.getIconWidth()); //$NON-NLS-1$
+			Assert.assertEquals("Wrong size.", size, baos.size()); //$NON-NLS-1$
 		} finally {
 			baos.close();
 		}
@@ -146,18 +143,35 @@
 
 	@Before
 	public void setUp() throws Exception {
+		startMetatype();
+		bundleInstaller = new BundleInstaller("bundle_tests/metatype", Activator.getBundleContext()); //$NON-NLS-1$
+	}
+
+	private void startMetatype() throws Exception {
 		Activator.getBundle(Activator.BUNDLE_METATYPE).start();
 		metaTypeReference = Activator.getBundleContext().getServiceReference(EquinoxMetaTypeService.class);
 		Assert.assertNotNull("Metatype service reference not found", metaTypeReference); //$NON-NLS-1$
 		metatype = Activator.getBundleContext().getService(metaTypeReference);
 		Assert.assertNotNull("Metatype service not found", metatype); //$NON-NLS-1$
-		bundleInstaller = new BundleInstaller("bundle_tests/metatype", Activator.getBundleContext()); //$NON-NLS-1$
 	}
 
 	@After
 	public void tearDown() throws Exception {
 		bundleInstaller.shutdown();
+		stopMetatype();
+	}
+
+	private void stopMetatype() throws Exception {
 		Activator.getBundleContext().ungetService(metaTypeReference);
 		Activator.getBundle(Activator.BUNDLE_METATYPE).stop();
 	}
+
+	public void restartMetatype() {
+		try {
+			stopMetatype();
+			startMetatype();
+		} catch (Exception e) {
+			fail(e.getMessage());
+		}
+	}
 }
diff --git a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/AttributeTypePasswordTest.java b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/AttributeTypePasswordTest.java
index e4587b5..3393f85 100644
--- a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/AttributeTypePasswordTest.java
+++ b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/AttributeTypePasswordTest.java
@@ -27,17 +27,17 @@
 		bundle.start();
 	}
 
-	@After
-	public void tearDown() throws Exception {
-		bundle.stop();
-		super.tearDown();
-	}
-
 	/*
 	 * Ensures the PASSWORD type is recognized.
 	 */
 	@Test
 	public void testAttributeTypePassword1() {
+		doTestAttributeTypePassword1();
+		restartMetatype();
+		doTestAttributeTypePassword1();
+	}
+
+	private void doTestAttributeTypePassword1() {
 		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		ObjectClassDefinition ocd = mti.getObjectClassDefinition("org.eclipse.equinox.metatype.tests.tb1", null); //$NON-NLS-1$
 		AttributeDefinition[] ads = ocd.getAttributeDefinitions(ObjectClassDefinition.ALL);
@@ -53,6 +53,12 @@
 	 */
 	@Test
 	public void testAttributeTypePassword2() {
+		doTestAttributeTypePassword2();
+		restartMetatype();
+		doTestAttributeTypePassword2();
+	}
+
+	private void doTestAttributeTypePassword2() {
 		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		ObjectClassDefinition ocd = mti.getObjectClassDefinition("org.eclipse.equinox.metatype.tests.tb1", null); //$NON-NLS-1$
 		AttributeDefinition[] ads = ocd.getAttributeDefinitions(ObjectClassDefinition.ALL);
@@ -66,6 +72,12 @@
 	 */
 	@Test
 	public void testAttributeTypePassword3() {
+		doTestAttributeTypePassword3();
+		restartMetatype();
+		doTestAttributeTypePassword3();
+	}
+
+	private void doTestAttributeTypePassword3() {
 		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		ObjectClassDefinition ocd = mti.getObjectClassDefinition("org.eclipse.equinox.metatype.tests.tb1", null); //$NON-NLS-1$
 		AttributeDefinition[] ads = ocd.getAttributeDefinitions(ObjectClassDefinition.ALL);
@@ -80,6 +92,12 @@
 	 */
 	@Test
 	public void testAttributeTypePassword4() {
+		doTestAttributeTypePassword4();
+		restartMetatype();
+		doTestAttributeTypePassword4();
+	}
+
+	private void doTestAttributeTypePassword4() {
 		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		ObjectClassDefinition ocd = mti.getObjectClassDefinition("org.eclipse.equinox.metatype.tests.tb1", null); //$NON-NLS-1$
 		AttributeDefinition[] ads = ocd.getAttributeDefinitions(ObjectClassDefinition.ALL);
@@ -95,6 +113,12 @@
 	 */
 	@Test
 	public void testAttributeTypePassword5() {
+		doTestAttributeTypePassword5();
+		restartMetatype();
+		doTestAttributeTypePassword5();
+	}
+
+	private void doTestAttributeTypePassword5() {
 		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		ObjectClassDefinition ocd = mti.getObjectClassDefinition("org.eclipse.equinox.metatype.tests.tb1", null); //$NON-NLS-1$
 		AttributeDefinition[] ads = ocd.getAttributeDefinitions(ObjectClassDefinition.ALL);
@@ -110,6 +134,12 @@
 	 */
 	@Test
 	public void testAttributeTypePassword6() {
+		doTestAttributeTypePassword6();
+		restartMetatype();
+		doTestAttributeTypePassword6();
+	}
+
+	private void doTestAttributeTypePassword6() {
 		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		ObjectClassDefinition ocd = mti.getObjectClassDefinition("org.eclipse.equinox.metatype.tests.tb1", null); //$NON-NLS-1$
 		AttributeDefinition[] ads = ocd.getAttributeDefinitions(ObjectClassDefinition.ALL);
diff --git a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/Bug332161Test.java b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/Bug332161Test.java
index 2e09342..472a747 100644
--- a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/Bug332161Test.java
+++ b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/Bug332161Test.java
@@ -109,6 +109,12 @@
 	 */
 	@Test
 	public void test1() {
+		doTest1();
+		restartMetatype();
+		doTest1();
+	}
+
+	private void doTest1() {
 		AttributeDefinition ad = findAttributeDefinitionById("char1", ads); //$NON-NLS-1$
 		Assert.assertNotNull("Attribute definition not found", ad); //$NON-NLS-1$
 		String defaultValue = getFirstDefaultValue(ad.getDefaultValue());
@@ -133,6 +139,12 @@
 	 */
 	@Test
 	public void test2() {
+		doTest2();
+		restartMetatype();
+		doTest2();
+	}
+
+	private void doTest2() {
 		AttributeDefinition ad = findAttributeDefinitionById("string1", ads); //$NON-NLS-1$
 		Assert.assertNotNull("Attribute definition not found", ad); //$NON-NLS-1$
 		String defaultValue = getFirstDefaultValue(ad.getDefaultValue());
@@ -148,6 +160,12 @@
 	 */
 	@Test
 	public void test3() {
+		doTest3();
+		restartMetatype();
+		doTest3();
+	}
+
+	private void doTest3() {
 		AttributeDefinition ad = findAttributeDefinitionById("string2", ads); //$NON-NLS-1$
 		Assert.assertNotNull("Attribute definition not found", ad); //$NON-NLS-1$
 		String[] defaultValue = ad.getDefaultValue();
@@ -186,6 +204,12 @@
 	 */
 	@Test
 	public void test4() {
+		doTest4();
+		restartMetatype();
+		doTest4();
+	}
+
+	private void doTest4() {
 		AttributeDefinition ad = findAttributeDefinitionById("string3", ads); //$NON-NLS-1$
 		Assert.assertNotNull("Attribute definition not found", ad); //$NON-NLS-1$
 		assertNull("Default value was not null", ad.getDefaultValue()); //$NON-NLS-1$
@@ -196,6 +220,12 @@
 	 */
 	@Test
 	public void test5() {
+		doTest5();
+		restartMetatype();
+		doTest5();
+	}
+
+	private void doTest5() {
 		AttributeDefinition ad = findAttributeDefinitionById("char2", ads); //$NON-NLS-1$
 		Assert.assertNotNull("Attribute definition not found", ad); //$NON-NLS-1$
 		assertNull("Default value was not null", ad.getDefaultValue()); //$NON-NLS-1$
@@ -208,6 +238,12 @@
 	 */
 	@Test
 	public void test6() {
+		doTest6();
+		restartMetatype();
+		doTest6();
+	}
+
+	private void doTest6() {
 		AttributeDefinition ad = findAttributeDefinitionById("string3", ads); //$NON-NLS-1$
 		Assert.assertNotNull("Attribute definition not found", ad); //$NON-NLS-1$
 		assertValidationFail(null, ad);
@@ -222,6 +258,12 @@
 	 */
 	@Test
 	public void test7() {
+		doTest7();
+		restartMetatype();
+		doTest7();
+	}
+
+	private void doTest7() {
 		AttributeDefinition ad = findAttributeDefinitionById("char3", ads); //$NON-NLS-1$
 		Assert.assertNotNull("Attribute definition not found", ad); //$NON-NLS-1$
 		assertValidationPass("\\\u0009", ad); //$NON-NLS-1$
@@ -242,6 +284,12 @@
 	 */
 	@Test
 	public void test8() {
+		doTest8();
+		restartMetatype();
+		doTest8();
+	}
+
+	private void doTest8() {
 		AttributeDefinition ad = findAttributeDefinitionById("string4", ads); //$NON-NLS-1$
 		Assert.assertNotNull("Attribute definition not found", ad); //$NON-NLS-1$
 		String[] defaultValue = ad.getDefaultValue();
@@ -262,6 +310,12 @@
 	 */
 	@Test
 	public void test9() {
+		doTest9();
+		restartMetatype();
+		doTest9();
+	}
+
+	private void doTest9() {
 		AttributeDefinition ad = findAttributeDefinitionById("integer1", ads); //$NON-NLS-1$
 		Assert.assertNotNull("Attribute definition not found", ad); //$NON-NLS-1$
 		String[] defaultValue = ad.getDefaultValue();
@@ -276,6 +330,12 @@
 	 */
 	@Test
 	public void test10() {
+		doTest10();
+		restartMetatype();
+		doTest10();
+	}
+
+	private void doTest10() {
 		AttributeDefinition ad = findAttributeDefinitionById("string5", ads); //$NON-NLS-1$
 		Assert.assertNotNull("Attribute definition not found", ad); //$NON-NLS-1$
 		String[] defaultValue = ad.getDefaultValue();
@@ -298,6 +358,10 @@
 		super.setUp();
 		bundle = bundleInstaller.installBundle("tb4"); //$NON-NLS-1$
 		bundle.start();
+		getMetatypeObjects();
+	}
+
+	private void getMetatypeObjects() {
 		mti = metatype.getMetaTypeInformation(bundle);
 		Assert.assertNotNull("Metatype information not found", mti); //$NON-NLS-1$
 		ocd = mti.getObjectClassDefinition("org.eclipse.equinox.metatype.tests.tb4", null); //$NON-NLS-1$
@@ -307,10 +371,10 @@
 		Assert.assertEquals("Wrong number of attribute definitions", 9, ads.length); //$NON-NLS-1$
 	}
 
-	@After
-	public void tearDown() throws Exception {
-		bundle.stop();
-		super.tearDown();
+	@Override
+	public void restartMetatype() {
+		super.restartMetatype();
+		getMetatypeObjects();
 	}
 
 	private void validateChar1Options(String[] optionLabels, String[] optionValues) {
diff --git a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/Bug340899Test.java b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/Bug340899Test.java
index bf9e3fb..d59c4fa 100644
--- a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/Bug340899Test.java
+++ b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/Bug340899Test.java
@@ -31,6 +31,12 @@
 	 */
 	@Test
 	public void test1() throws Exception {
+		doTest1();
+		restartMetatype();
+		doTest1();
+	}
+
+	private void doTest1() throws Exception {
 		execute("tb5", "org.eclipse.equinox.metatype.tests.tb5"); //$NON-NLS-1$ //$NON-NLS-2$
 	}
 
@@ -41,6 +47,12 @@
 	 */
 	@Test
 	public void test2() throws Exception {
+		doTest2();
+		restartMetatype();
+		doTest2();
+	}
+
+	private void doTest2() throws Exception {
 		execute("tb6", "org.eclipse.equinox.metatype.tests.tb6"); //$NON-NLS-1$ //$NON-NLS-2$
 	}
 
@@ -51,6 +63,12 @@
 	 */
 	@Test
 	public void test3() throws Exception {
+		doTest3();
+		restartMetatype();
+		doTest3();
+	}
+
+	private void doTest3() throws Exception {
 		execute("tb7", "org.eclipse.equinox.metatype.tests.tb7"); //$NON-NLS-1$ //$NON-NLS-2$
 	}
 
diff --git a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/Bug395196Test.java b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/Bug395196Test.java
index f34069f..86aa989 100644
--- a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/Bug395196Test.java
+++ b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/Bug395196Test.java
@@ -34,7 +34,13 @@
 	private ObjectClassDefinition ocd;
 
 	@Test
-	public void testRejectDefaultValueWhenNotAnOption() {
+	public void testRejectDefaultValueWhenNotAnOption() throws Exception {
+		doTestRejectDefaultValueWhenNotAnOption();
+		restartMetatype();
+		doTestRejectDefaultValueWhenNotAnOption();
+	}
+
+	private void doTestRejectDefaultValueWhenNotAnOption() {
 		AttributeDefinition ad = findAttributeDefinitionById("ocd3-ad1", ads); //$NON-NLS-1$
 		Assert.assertNotNull("Attribute definition not found", ad); //$NON-NLS-1$
 		assertNull("Default value not matching one of the options was not rejected", ad.getDefaultValue()); //$NON-NLS-1$
@@ -45,6 +51,10 @@
 		super.setUp();
 		bundle = bundleInstaller.installBundle("tb1"); //$NON-NLS-1$
 		bundle.start();
+		getMetaTypeObjects();
+	}
+
+	private void getMetaTypeObjects() {
 		mti = metatype.getMetaTypeInformation(bundle);
 		Assert.assertNotNull("Metatype information not found", mti); //$NON-NLS-1$
 		ocd = mti.getObjectClassDefinition("org.eclipse.equinox.metatype.tests.tb1.testRejectDefaultValueWhenNotAnOption", null); //$NON-NLS-1$
@@ -54,9 +64,9 @@
 		Assert.assertEquals("Wrong number of attribute definitions", 1, ads.length); //$NON-NLS-1$
 	}
 
-	@After
-	public void tearDown() throws Exception {
-		bundle.stop();
-		super.tearDown();
+	@Override
+	public void restartMetatype() {
+		super.restartMetatype();
+		getMetaTypeObjects();
 	}
 }
diff --git a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/BugTests.java b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/BugTests.java
index 26ad500..94e9d5c 100644
--- a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/BugTests.java
+++ b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/BugTests.java
@@ -27,7 +27,13 @@
 	 * A cardinality of zero should not require a default value to be specified.
 	 */
 	@Test
-	public void test334642() {
+	public void test334642() throws Exception {
+		doTest334642();
+		restartMetatype();
+		doTest334642();
+	}
+
+	private void doTest334642() {
 		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		Assert.assertNotNull("Metatype information not found", mti); //$NON-NLS-1$
 		ObjectClassDefinition ocd = mti.getObjectClassDefinition("org.eclipse.equinox.metatype.tests.tb3", null); //$NON-NLS-1$
@@ -62,7 +68,13 @@
 	 * StringIndexOutOfBoundsException when description or name attributes are an empty string
 	 */
 	@Test
-	public void test341963() {
+	public void test341963() throws Exception {
+		doTest341963();
+		restartMetatype();
+		doTest341963();
+	}
+
+	private void doTest341963() {
 		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		Assert.assertNotNull("Metatype information not found", mti); //$NON-NLS-1$
 		ObjectClassDefinition ocd = mti.getObjectClassDefinition("ocd2", null); //$NON-NLS-1$
@@ -86,9 +98,4 @@
 		bundle.start();
 	}
 
-	@After
-	public void tearDown() throws Exception {
-		bundle.stop();
-		super.tearDown();
-	}
 }
diff --git a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/ExtendableTest.java b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/ExtendableTest.java
index 2aabe9b..899a3d6 100644
--- a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/ExtendableTest.java
+++ b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/ExtendableTest.java
@@ -33,7 +33,13 @@
 	}
 
 	@Test
-	public void testExtensions() {
+	public void testExtensions() throws Exception {
+		doTestExtensions();
+		restartMetatype();
+		doTestExtensions();
+	}
+
+	private void doTestExtensions() {
 		EquinoxMetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		EquinoxObjectClassDefinition ocd = mti.getObjectClassDefinition("metatype.extendable.tb1.1", null); //$NON-NLS-1$
 		Set<String> schemas = ocd.getExtensionUris();
diff --git a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/GetDefaultValueTest.java b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/GetDefaultValueTest.java
index c09b4a9..83c3ede 100644
--- a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/GetDefaultValueTest.java
+++ b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/GetDefaultValueTest.java
@@ -30,7 +30,13 @@
 	private Bundle bundle;
 
 	@Test
-	public void testGetDefaultValue() {
+	public void testGetDefaultValue() throws Exception {
+		doTestGetDefaultValue();
+		restartMetatype();
+		doTestGetDefaultValue();
+	}
+
+	private void doTestGetDefaultValue() {
 		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		Assert.assertNotNull("Metatype information was null", mti); //$NON-NLS-1$
 		ObjectClassDefinition ocd = mti.getObjectClassDefinition("org.eclipse.equinox.metatype.tests.tb1.getDefaultValues", null); //$NON-NLS-1$
diff --git a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/IconTest.java b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/IconTest.java
index 4226a64..c72dfde 100644
--- a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/IconTest.java
+++ b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/IconTest.java
@@ -15,7 +15,8 @@
 
 import static org.junit.Assert.assertNull;
 
-import org.junit.*;
+import org.junit.Before;
+import org.junit.Test;
 import org.osgi.framework.Bundle;
 import org.osgi.service.metatype.*;
 
@@ -38,6 +39,12 @@
 
 	@Test
 	public void testIcon() throws Exception {
+		doTestIcon();
+		restartMetatype();
+		doTestIcon();
+	}
+
+	private void doTestIcon() throws Exception {
 		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		assertNotNull(mti);
 		ObjectClassDefinition ocd = mti.getObjectClassDefinition("org.eclipse.equinox.metatype.tests.tb9", null); //$NON-NLS-1$
@@ -45,19 +52,23 @@
 		AttributeDefinition[] ads = ocd.getAttributeDefinitions(ObjectClassDefinition.ALL);
 		assertAttributeDefinitions(ads, 1);
 		assertAttributeDefinition(ads[0], 0, null, null, "1", "ad1", null, null, AttributeDefinition.STRING); //$NON-NLS-1$ //$NON-NLS-2$
-		assertIcon(ocd.getIcon(10000), 10000);
-		assertIcon(ocd.getIcon(22500), 22500);
-		assertIcon(ocd.getIcon(40000), 40000);
-		assertIcon(ocd.getIcon(5000), 10000);
-		assertIcon(ocd.getIcon(50000), 40000);
-		assertIcon(ocd.getIcon(16249), 10000);
-		assertIcon(ocd.getIcon(16251), 22500);
-		assertIcon(ocd.getIcon(31249), 22500);
-		assertIcon(ocd.getIcon(31251), 40000);
+		assertIcon(ocd.getIcon(4931), 4931);
+		assertIcon(ocd.getIcon(7933), 7933);
+		assertIcon(ocd.getIcon(10182), 10182);
+		assertIcon(ocd.getIcon(5000), 4931);
+		assertIcon(ocd.getIcon(50000), 10182);
+		assertIcon(ocd.getIcon(6400), 4931);
+		assertIcon(ocd.getIcon(6500), 7933);
 	}
 
 	@Test
 	public void testNullIcon() throws Exception {
+		doTestNullIcon();
+		restartMetatype();
+		doTestNullIcon();
+	}
+
+	private void doTestNullIcon() throws Exception {
 		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		assertNotNull(mti);
 		ObjectClassDefinition ocd = mti.getObjectClassDefinition("org.eclipse.equinox.metatype.tests.tb9.2", null); //$NON-NLS-1$
@@ -73,10 +84,4 @@
 		super.setUp();
 		bundle = bundleInstaller.installBundle("tb9"); //$NON-NLS-1$
 	}
-
-	@After
-	public void tearDown() throws Exception {
-		bundle.uninstall();
-		super.tearDown();
-	}
 }
diff --git a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/NoADTest.java b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/NoADTest.java
index e8a1d6b..35ec280 100755
--- a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/NoADTest.java
+++ b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/NoADTest.java
@@ -13,38 +13,17 @@
  *******************************************************************************/
 package org.eclipse.equinox.metatype.tests;
 
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-
-import org.eclipse.equinox.compendium.tests.Activator;
-import org.eclipse.osgi.tests.bundles.BundleInstaller;
 import org.junit.*;
 import org.osgi.framework.Bundle;
-import org.osgi.framework.ServiceReference;
 import org.osgi.service.metatype.*;
 
-public class NoADTest {
+public class NoADTest extends AbstractTest {
 	private Bundle bundle;
-	private BundleInstaller bundleInstaller;
-	private MetaTypeService metaType;
-	private ServiceReference<MetaTypeService> metaTypeReference;
 
 	@Before
 	public void setUp() throws Exception {
-		Activator.getBundle(Activator.BUNDLE_METATYPE).start();
-		metaTypeReference = Activator.getBundleContext().getServiceReference(MetaTypeService.class);
-		metaType = Activator.getBundleContext().getService(metaTypeReference);
-		bundleInstaller = new BundleInstaller("bundle_tests/metatype", Activator.getBundleContext()); //$NON-NLS-1$
-		bundleInstaller.refreshPackages(null);
+		super.setUp();
 		bundle = bundleInstaller.installBundle("tb10"); //$NON-NLS-1$
-		bundle.start();
-	}
-
-	@After
-	public void tearDown() throws Exception {
-		bundleInstaller.shutdown();
-		Activator.getBundleContext().ungetService(metaTypeReference);
-		Activator.getBundle(Activator.BUNDLE_METATYPE).stop();
 	}
 
 	/*
@@ -52,17 +31,23 @@
 	 */
 	@Test
 	public void testNoADs() {
-		MetaTypeInformation mti = metaType.getMetaTypeInformation(bundle);
+		doTestNoADs();
+		restartMetatype();
+		doTestNoADs();
+	}
+
+	private void doTestNoADs() {
+		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		String[] pids = mti.getPids();
-		assertNotNull("The pid was not present.", pids); //$NON-NLS-1$
-		assertEquals("Not the expected number of pids.", 1, pids.length); //$NON-NLS-1$
-		assertEquals("Expected pid was not present.", "no.ad.designate", pids[0]); //$NON-NLS-1$ //$NON-NLS-2$
+		Assert.assertNotNull("The pid was not present.", pids); //$NON-NLS-1$
+		Assert.assertEquals("Not the expected number of pids.", 1, pids.length); //$NON-NLS-1$
+		Assert.assertEquals("Expected pid was not present.", "no.ad.designate", pids[0]); //$NON-NLS-1$ //$NON-NLS-2$
 		ObjectClassDefinition ocd = mti.getObjectClassDefinition(pids[0], null);
 		AttributeDefinition[] ads = ocd.getAttributeDefinitions(ObjectClassDefinition.ALL);
 		// seems we are not really spec compliant here
 		if (ads != null) {
 			// should really be null, but if not then make sure it is an empty array
-			assertEquals("Found some ads: " + ads, 0, ads.length); //$NON-NLS-1$
+			Assert.assertEquals("Found some ads: " + ads, 0, ads.length); //$NON-NLS-1$
 		}
 	}
 }
diff --git a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/SameOcdPidFactoryPidTest.java b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/SameOcdPidFactoryPidTest.java
index b20bf8b..64cd7dc 100644
--- a/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/SameOcdPidFactoryPidTest.java
+++ b/bundles/org.eclipse.equinox.compendium.tests/src/org/eclipse/equinox/metatype/tests/SameOcdPidFactoryPidTest.java
@@ -13,41 +13,20 @@
  *******************************************************************************/
 package org.eclipse.equinox.metatype.tests;
 
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-
-import org.eclipse.equinox.compendium.tests.Activator;
-import org.eclipse.osgi.tests.bundles.BundleInstaller;
 import org.junit.*;
 import org.osgi.framework.Bundle;
-import org.osgi.framework.ServiceReference;
 import org.osgi.service.metatype.MetaTypeInformation;
-import org.osgi.service.metatype.MetaTypeService;
 
-public class SameOcdPidFactoryPidTest {
+public class SameOcdPidFactoryPidTest extends AbstractTest {
 	private Bundle bundle;
-	private BundleInstaller bundleInstaller;
-	private MetaTypeService metaType;
-	private ServiceReference<MetaTypeService> metaTypeReference;
 
 	@Before
 	public void setUp() throws Exception {
-		Activator.getBundle(Activator.BUNDLE_METATYPE).start();
-		metaTypeReference = Activator.getBundleContext().getServiceReference(MetaTypeService.class);
-		metaType = Activator.getBundleContext().getService(metaTypeReference);
-		bundleInstaller = new BundleInstaller("bundle_tests/metatype", Activator.getBundleContext()); //$NON-NLS-1$
-		bundleInstaller.refreshPackages(null);
+		super.setUp();
 		bundle = bundleInstaller.installBundle("tb2"); //$NON-NLS-1$
 		bundle.start();
 	}
 
-	@After
-	public void tearDown() throws Exception {
-		bundleInstaller.shutdown();
-		Activator.getBundleContext().ungetService(metaTypeReference);
-		Activator.getBundle(Activator.BUNDLE_METATYPE).stop();
-	}
-
 	/*
 	 * Ensures the same OCD referred to by two Designate elements, one using
 	 * the factoryPid attribute and the other only the pid attribute, is
@@ -55,14 +34,20 @@
 	 */
 	@Test
 	public void test1() {
-		MetaTypeInformation mti = metaType.getMetaTypeInformation(bundle);
+		doTest1();
+		restartMetatype();
+		doTest1();
+	}
+
+	private void doTest1() {
+		MetaTypeInformation mti = metatype.getMetaTypeInformation(bundle);
 		String[] pids = mti.getPids();
-		assertNotNull("The pid 'singleton' was not present.", pids); //$NON-NLS-1$
-		assertEquals("Not the expected number of pids.", 1, pids.length); //$NON-NLS-1$
-		assertEquals("Expected pid was not present.", "singleton", pids[0]); //$NON-NLS-1$ //$NON-NLS-2$
+		Assert.assertNotNull("The pid 'singleton' was not present.", pids); //$NON-NLS-1$
+		Assert.assertEquals("Not the expected number of pids.", 1, pids.length); //$NON-NLS-1$
+		Assert.assertEquals("Expected pid was not present.", "singleton", pids[0]); //$NON-NLS-1$ //$NON-NLS-2$
 		String[] factoryPids = mti.getFactoryPids();
-		assertNotNull("The factory pid 'factory' was not present.", factoryPids); //$NON-NLS-1$
-		assertEquals("Not the expected number of factory pids.", 1, factoryPids.length); //$NON-NLS-1$
-		assertEquals("Expected factory pid was not present.", "factory", factoryPids[0]); //$NON-NLS-1$ //$NON-NLS-2$
+		Assert.assertNotNull("The factory pid 'factory' was not present.", factoryPids); //$NON-NLS-1$
+		Assert.assertEquals("Not the expected number of factory pids.", 1, factoryPids.length); //$NON-NLS-1$
+		Assert.assertEquals("Expected factory pid was not present.", "factory", factoryPids[0]); //$NON-NLS-1$ //$NON-NLS-2$
 	}
 }
diff --git a/bundles/org.eclipse.equinox.metatype/.classpath b/bundles/org.eclipse.equinox.metatype/.classpath
index 64c5e31..098194c 100644
--- a/bundles/org.eclipse.equinox.metatype/.classpath
+++ b/bundles/org.eclipse.equinox.metatype/.classpath
@@ -1,6 +1,6 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <classpath>
-	<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/J2SE-1.5"/>
+	<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-1.7"/>
 	<classpathentry kind="con" path="org.eclipse.pde.core.requiredPlugins"/>
 	<classpathentry kind="src" path="src"/>
 	<classpathentry kind="output" path="bin"/>
diff --git a/bundles/org.eclipse.equinox.metatype/.settings/org.eclipse.jdt.core.prefs b/bundles/org.eclipse.equinox.metatype/.settings/org.eclipse.jdt.core.prefs
index a0668fa..2c87a2b 100644
--- a/bundles/org.eclipse.equinox.metatype/.settings/org.eclipse.jdt.core.prefs
+++ b/bundles/org.eclipse.equinox.metatype/.settings/org.eclipse.jdt.core.prefs
@@ -13,9 +13,9 @@
 org.eclipse.jdt.core.compiler.annotation.nullable=org.eclipse.jdt.annotation.Nullable
 org.eclipse.jdt.core.compiler.annotation.nullanalysis=disabled
 org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
-org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.5
+org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.7
 org.eclipse.jdt.core.compiler.codegen.unusedLocal=preserve
-org.eclipse.jdt.core.compiler.compliance=1.5
+org.eclipse.jdt.core.compiler.compliance=1.7
 org.eclipse.jdt.core.compiler.debug.lineNumber=generate
 org.eclipse.jdt.core.compiler.debug.localVariable=generate
 org.eclipse.jdt.core.compiler.debug.sourceFile=generate
@@ -113,23 +113,27 @@
 org.eclipse.jdt.core.compiler.problem.unusedTypeParameter=ignore
 org.eclipse.jdt.core.compiler.problem.unusedWarningToken=warning
 org.eclipse.jdt.core.compiler.problem.varargsArgumentNeedCast=warning
-org.eclipse.jdt.core.compiler.source=1.5
+org.eclipse.jdt.core.compiler.source=1.7
 org.eclipse.jdt.core.formatter.align_type_members_on_columns=false
+org.eclipse.jdt.core.formatter.alignment_for_additive_operator=16
 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression=16
 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant=16
 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call=16
 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation=16
 org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression=16
 org.eclipse.jdt.core.formatter.alignment_for_assignment=0
-org.eclipse.jdt.core.formatter.alignment_for_binary_expression=16
+org.eclipse.jdt.core.formatter.alignment_for_bitwise_operator=16
 org.eclipse.jdt.core.formatter.alignment_for_compact_if=16
 org.eclipse.jdt.core.formatter.alignment_for_conditional_expression=80
 org.eclipse.jdt.core.formatter.alignment_for_enum_constants=0
 org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer=16
+org.eclipse.jdt.core.formatter.alignment_for_logical_operator=16
 org.eclipse.jdt.core.formatter.alignment_for_multiple_fields=16
+org.eclipse.jdt.core.formatter.alignment_for_multiplicative_operator=16
 org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration=16
 org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration=16
 org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation=16
+org.eclipse.jdt.core.formatter.alignment_for_string_concatenation=16
 org.eclipse.jdt.core.formatter.alignment_for_superclass_in_type_declaration=16
 org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration=16
 org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration=16
@@ -199,11 +203,12 @@
 org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_declaration=insert
 org.eclipse.jdt.core.formatter.insert_new_line_in_empty_method_body=insert
 org.eclipse.jdt.core.formatter.insert_new_line_in_empty_type_declaration=insert
+org.eclipse.jdt.core.formatter.insert_space_after_additive_operator=insert
 org.eclipse.jdt.core.formatter.insert_space_after_and_in_type_parameter=insert
 org.eclipse.jdt.core.formatter.insert_space_after_assignment_operator=insert
 org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation=do not insert
 org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation_type_declaration=do not insert
-org.eclipse.jdt.core.formatter.insert_space_after_binary_operator=insert
+org.eclipse.jdt.core.formatter.insert_space_after_bitwise_operator=insert
 org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_arguments=insert
 org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_parameters=insert
 org.eclipse.jdt.core.formatter.insert_space_after_closing_brace_in_block=insert
@@ -233,6 +238,8 @@
 org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_arguments=insert
 org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_parameters=insert
 org.eclipse.jdt.core.formatter.insert_space_after_ellipsis=insert
+org.eclipse.jdt.core.formatter.insert_space_after_logical_operator=insert
+org.eclipse.jdt.core.formatter.insert_space_after_multiplicative_operator=insert
 org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_parameterized_type_reference=do not insert
 org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_arguments=do not insert
 org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_parameters=do not insert
@@ -256,12 +263,16 @@
 org.eclipse.jdt.core.formatter.insert_space_after_prefix_operator=do not insert
 org.eclipse.jdt.core.formatter.insert_space_after_question_in_conditional=insert
 org.eclipse.jdt.core.formatter.insert_space_after_question_in_wildcard=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_relational_operator=insert
 org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_for=insert
+org.eclipse.jdt.core.formatter.insert_space_after_shift_operator=insert
+org.eclipse.jdt.core.formatter.insert_space_after_string_concatenation=insert
 org.eclipse.jdt.core.formatter.insert_space_after_unary_operator=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_additive_operator=insert
 org.eclipse.jdt.core.formatter.insert_space_before_and_in_type_parameter=insert
 org.eclipse.jdt.core.formatter.insert_space_before_assignment_operator=insert
 org.eclipse.jdt.core.formatter.insert_space_before_at_in_annotation_type_declaration=insert
-org.eclipse.jdt.core.formatter.insert_space_before_binary_operator=insert
+org.eclipse.jdt.core.formatter.insert_space_before_bitwise_operator=insert
 org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_parameterized_type_reference=do not insert
 org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_arguments=do not insert
 org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_parameters=do not insert
@@ -307,6 +318,8 @@
 org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_arguments=do not insert
 org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_parameters=do not insert
 org.eclipse.jdt.core.formatter.insert_space_before_ellipsis=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_logical_operator=insert
+org.eclipse.jdt.core.formatter.insert_space_before_multiplicative_operator=insert
 org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_parameterized_type_reference=do not insert
 org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_arguments=do not insert
 org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_parameters=do not insert
@@ -342,8 +355,11 @@
 org.eclipse.jdt.core.formatter.insert_space_before_prefix_operator=do not insert
 org.eclipse.jdt.core.formatter.insert_space_before_question_in_conditional=insert
 org.eclipse.jdt.core.formatter.insert_space_before_question_in_wildcard=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_relational_operator=insert
 org.eclipse.jdt.core.formatter.insert_space_before_semicolon=do not insert
 org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_for=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_shift_operator=insert
+org.eclipse.jdt.core.formatter.insert_space_before_string_concatenation=insert
 org.eclipse.jdt.core.formatter.insert_space_before_unary_operator=do not insert
 org.eclipse.jdt.core.formatter.insert_space_between_brackets_in_array_type_reference=do not insert
 org.eclipse.jdt.core.formatter.insert_space_between_empty_braces_in_array_initializer=do not insert
@@ -366,6 +382,10 @@
 org.eclipse.jdt.core.formatter.tabulation.char=tab
 org.eclipse.jdt.core.formatter.tabulation.size=4
 org.eclipse.jdt.core.formatter.use_tabs_only_for_leading_indentations=false
-org.eclipse.jdt.core.formatter.wrap_before_binary_operator=true
+org.eclipse.jdt.core.formatter.wrap_before_additive_operator=true
+org.eclipse.jdt.core.formatter.wrap_before_bitwise_operator=true
+org.eclipse.jdt.core.formatter.wrap_before_logical_operator=true
+org.eclipse.jdt.core.formatter.wrap_before_multiplicative_operator=true
+org.eclipse.jdt.core.formatter.wrap_before_string_concatenation=true
 org.eclipse.jdt.core.incompatibleJDKLevel=ignore
 org.eclipse.jdt.core.incompleteClasspath=error
diff --git a/bundles/org.eclipse.equinox.metatype/META-INF/MANIFEST.MF b/bundles/org.eclipse.equinox.metatype/META-INF/MANIFEST.MF
index 5fe4a40..8b6a6e6 100644
--- a/bundles/org.eclipse.equinox.metatype/META-INF/MANIFEST.MF
+++ b/bundles/org.eclipse.equinox.metatype/META-INF/MANIFEST.MF
@@ -1,6 +1,6 @@
 Bundle-ManifestVersion: 2
 Bundle-Name: %bundleName
-Bundle-Version: 1.4.600.qualifier
+Bundle-Version: 1.5.0.qualifier
 Bundle-SymbolicName: org.eclipse.equinox.metatype
 Bundle-Activator: org.eclipse.equinox.metatype.impl.Activator
 Import-Package: javax.xml.parsers,
@@ -17,7 +17,7 @@
  org.eclipse.equinox.metatype.impl;version="1.3.0";x-friends:=org.eclipse.equinox.compendium.tests
 Bundle-Vendor: %bundleVendor
 Bundle-Localization: plugin
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
+Bundle-RequiredExecutionEnvironment: JavaSE-1.7
 Provide-Capability: osgi.implementation;
   osgi.implementation="osgi.metatype";
   version:Version="1.4";
diff --git a/bundles/org.eclipse.equinox.metatype/pom.xml b/bundles/org.eclipse.equinox.metatype/pom.xml
index 84475fc..823b3ee 100644
--- a/bundles/org.eclipse.equinox.metatype/pom.xml
+++ b/bundles/org.eclipse.equinox.metatype/pom.xml
@@ -19,7 +19,7 @@
   </parent>
   <groupId>org.eclipse.equinox</groupId>
   <artifactId>org.eclipse.equinox.metatype</artifactId>
-  <version>1.4.600-SNAPSHOT</version>
+  <version>1.5.0-SNAPSHOT</version>
   <packaging>eclipse-plugin</packaging>
   <build>
     <plugins>
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/Activator.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/Activator.java
index 17ec158..446523d 100644
--- a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/Activator.java
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/Activator.java
@@ -13,13 +13,13 @@
  *******************************************************************************/
 package org.eclipse.equinox.metatype.impl;
 
+import java.io.IOException;
 import java.util.Dictionary;
 import java.util.Hashtable;
 import javax.xml.parsers.SAXParserFactory;
 import org.eclipse.equinox.metatype.EquinoxMetaTypeService;
 import org.osgi.framework.*;
 import org.osgi.service.cm.ManagedService;
-import org.osgi.service.log.LogService;
 import org.osgi.service.metatype.MetaTypeProvider;
 import org.osgi.service.metatype.MetaTypeService;
 import org.osgi.util.tracker.ServiceTracker;
@@ -64,7 +64,7 @@
 		}
 		// Do this first to make logging available as early as possible.
 		lsTracker.open();
-		lsTracker.log(LogService.LOG_DEBUG, "====== Meta Type Service starting ! ====="); //$NON-NLS-1$
+		lsTracker.log(LogTracker.LOG_DEBUG, "====== Meta Type Service starting ! ====="); //$NON-NLS-1$
 		// Do this next to make MetaTypeProviders available as early as possible.
 		mtpTracker.open();
 		// Do this last because it may result in the MetaTypeService being registered.
@@ -84,7 +84,7 @@
 			mtpTracker = metaTypeProviderTracker;
 			lsTracker = logServiceTracker;
 		}
-		lsTracker.log(LogService.LOG_DEBUG, "====== Meta Type Service stopping ! ====="); //$NON-NLS-1$
+		lsTracker.log(LogTracker.LOG_DEBUG, "====== Meta Type Service stopping ! ====="); //$NON-NLS-1$
 		spfTracker.close();
 		mtpTracker.close();
 		// Do this last to leave logging available as long as possible.
@@ -228,6 +228,11 @@
 				service = metaTypeService = new MetaTypeServiceImpl(saxParserFactory, logService, mtpTracker);
 			}
 			bundleCtx.addBundleListener(service);
+			try {
+				service.load(bundleCtx, logService, mtpTracker);
+			} catch (IOException e) {
+				logService.log(LogTracker.LOG_ERROR, "Error loading cached metatype info.", e); //$NON-NLS-1$
+			}
 			ServiceRegistration<?> registration = bundleCtx.registerService(new String[] {MetaTypeService.class.getName(), EquinoxMetaTypeService.class.getName()}, service, properties);
 			synchronized (this) {
 				metaTypeServiceRegistration = registration;
@@ -252,6 +257,11 @@
 		private void unregisterMetaTypeService(ServiceRegistration<?> registration, MetaTypeServiceImpl service) {
 			registration.unregister();
 			bundleCtx.removeBundleListener(service);
+			try {
+				service.save(bundleCtx);
+			} catch (IOException e) {
+				logService.log(LogTracker.LOG_ERROR, "Error saving metatype cache.", e); //$NON-NLS-1$
+			}
 		}
 	}
 }
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/AttributeDefinitionImpl.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/AttributeDefinitionImpl.java
index ad2c009..7334b3e 100644
--- a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/AttributeDefinitionImpl.java
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/AttributeDefinitionImpl.java
@@ -13,32 +13,37 @@
  *******************************************************************************/
 package org.eclipse.equinox.metatype.impl;
 
+import java.io.IOException;
+import java.math.BigDecimal;
+import java.math.BigInteger;
 import java.util.*;
 import org.eclipse.equinox.metatype.EquinoxAttributeDefinition;
+import org.eclipse.equinox.metatype.impl.Persistence.Reader;
+import org.eclipse.equinox.metatype.impl.Persistence.Writer;
 import org.eclipse.osgi.util.NLS;
-import org.osgi.service.log.LogService;
+import org.osgi.service.metatype.AttributeDefinition;
 
 /**
  * Implementation of AttributeDefintion
  */
 public class AttributeDefinitionImpl extends LocalizationElement implements EquinoxAttributeDefinition, Cloneable {
 
-	String _name;
-	String _id;
-	String _description;
-	int _cardinality = 0;
-	int _dataType;
-	Object _minValue = null;
-	Object _maxValue = null;
-	boolean _isRequired = true;
-
-	String[] _defaults = null;
-	Vector<String> _values = new Vector<String>(7);
-	Vector<String> _labels = new Vector<String>(7);
+	private final String _name;
+	private final String _id;
+	private final String _description;
+	private final int _cardinality;
+	private final int _dataType;
+	private final Object _minValue;
+	private final Object _maxValue;
+	private final boolean _isRequired;
 
 	private final LogTracker logger;
 	private final ExtendableHelper helper;
 
+	private volatile String[] _defaults = null;
+	private volatile ArrayList<String> _values = new ArrayList<String>(7);
+	private volatile ArrayList<String> _labels = new ArrayList<String>(7);
+
 	/**
 	 * Constructor of class AttributeDefinitionImpl.
 	 */
@@ -63,20 +68,20 @@
 	/*
 	 * 
 	 */
-	public synchronized Object clone() {
+	public Object clone() {
 
 		AttributeDefinitionImpl ad = new AttributeDefinitionImpl(_id, _name, _description, _dataType, _cardinality, _minValue, _maxValue, _isRequired, getLocalization(), logger, helper);
 
-		if (_defaults != null) {
-			ad.setDefaultValue(_defaults.clone());
+		String[] curDefaults = _defaults;
+		if (curDefaults != null) {
+			ad.setDefaultValue(curDefaults.clone());
 		}
-		if ((_labels != null) && (_values != null)) {
-			@SuppressWarnings("unchecked")
-			Vector<String> labels = (Vector<String>) _labels.clone();
-			@SuppressWarnings("unchecked")
-			Vector<String> values = (Vector<String>) _values.clone();
-			ad.setOption(labels, values, false);
-		}
+
+		@SuppressWarnings("unchecked")
+		ArrayList<String> labels = (ArrayList<String>) _labels.clone();
+		@SuppressWarnings("unchecked")
+		ArrayList<String> values = (ArrayList<String>) _values.clone();
+		ad.setOption(labels, values, false);
 
 		return ad;
 	}
@@ -90,13 +95,6 @@
 		return getLocalized(_name);
 	}
 
-	/**
-	 * Method to set the name of AttributeDefinition.
-	 */
-	void setName(String name) {
-		this._name = name;
-	}
-
 	/*
 	 * (non-Javadoc)
 	 * 
@@ -106,13 +104,6 @@
 		return _id;
 	}
 
-	/**
-	 * Method to set the ID of AttributeDefinition.
-	 */
-	void setID(String id) {
-		this._id = id;
-	}
-
 	/*
 	 * (non-Javadoc)
 	 * 
@@ -122,13 +113,6 @@
 		return getLocalized(_description);
 	}
 
-	/**
-	 * Method to set the description of AttributeDefinition.
-	 */
-	void setDescription(String description) {
-		this._description = description;
-	}
-
 	/*
 	 * (non-Javadoc)
 	 * 
@@ -138,13 +122,6 @@
 		return _cardinality;
 	}
 
-	/**
-	 * Method to set the cardinality of AttributeDefinition.
-	 */
-	void setCardinality(int cardinality) {
-		this._cardinality = cardinality;
-	}
-
 	/*
 	 * (non-Javadoc)
 	 * 
@@ -155,26 +132,12 @@
 	}
 
 	/**
-	 * Method to set the data type of AttributeDefinition.
-	 */
-	void setType(int type) {
-		this._dataType = type;
-	}
-
-	/**
 	 * Method to get the required flag of AttributeDefinition.
 	 */
 	boolean isRequired() {
 		return _isRequired;
 	}
 
-	/**
-	 * Method to set the required flag of AttributeDefinition.
-	 */
-	void setRequired(boolean isRequired) {
-		this._isRequired = isRequired;
-	}
-
 	/*
 	 * (non-Javadoc)
 	 * 
@@ -182,15 +145,14 @@
 	 */
 	public String[] getOptionLabels() {
 
-		if ((_labels == null) || (_labels.size() == 0)) {
+		List<String> curLabels = _labels;
+		if (curLabels.isEmpty()) {
 			return null;
 		}
 
-		String[] returnedLabels = new String[_labels.size()];
-		Enumeration<String> labelKeys = _labels.elements();
+		String[] returnedLabels = new String[curLabels.size()];
 		int i = 0;
-		while (labelKeys.hasMoreElements()) {
-			String labelKey = labelKeys.nextElement();
+		for (String labelKey : curLabels) {
 			returnedLabels[i] = getLocalized(labelKey);
 			i++;
 		}
@@ -203,41 +165,47 @@
 	 * @see org.osgi.service.metatype.AttributeDefinition#getOptionValues()
 	 */
 	public String[] getOptionValues() {
+		List<String> curValues = _values;
 
-		if ((_values == null) || (_values.size() == 0)) {
+		if (curValues.isEmpty()) {
 			return null;
 		}
 
-		return _values.toArray(new String[_values.size()]);
+		return curValues.toArray(MetaTypeInformationImpl.emptyStringArray);
 	}
 
 	/**
 	 * Method to set the Option values of AttributeDefinition.
 	 */
-	void setOption(Vector<String> labels, Vector<String> values, boolean needValidation) {
+	void setOption(ArrayList<String> labels, ArrayList<String> values, boolean needValidation) {
 		if ((labels == null) || (values == null)) {
-			logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.NULL_OPTIONS, getID()));
+			logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.NULL_OPTIONS, getID()));
 			return;
 		}
 		if (labels.size() != values.size()) {
-			logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.INCONSISTENT_OPTIONS, getID()));
+			logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.INCONSISTENT_OPTIONS, getID()));
 			return;
 		}
-		_labels = labels;
-		_values = values;
 		if (needValidation) {
-			for (int index = 0; index < _values.size(); index++) {
-				ValueTokenizer vt = new ValueTokenizer(_values.get(index), logger);
-				_values.set(index, vt.getValuesAsString());
+			for (int index = 0; index < values.size(); index++) {
+				ValueTokenizer vt = new ValueTokenizer(values.get(index), logger);
+				values.set(index, vt.getValuesAsString());
 				String reason = vt.validate(this);
 				if ((reason != null) && reason.length() > 0) {
-					logger.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.INVALID_OPTIONS, new Object[] {_values.get(index), getID(), reason}));
-					_labels.remove(index);
-					_values.remove(index);
+					logger.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.INVALID_OPTIONS, new Object[] {values.get(index), getID(), reason}));
+					labels.remove(index);
+					values.remove(index);
 					index--; // Because this one has been removed.
 				}
 			}
 		}
+		_labels = labels;
+		_values = values;
+	}
+
+	boolean containsInvalidValue(String value) {
+		List<String> curValues = _values;
+		return !curValues.isEmpty() && !curValues.contains(value);
 	}
 
 	/*
@@ -257,7 +225,7 @@
 		ValueTokenizer vt = new ValueTokenizer(defaults_str, logger);
 		String reason = vt.validate(this);
 		if ((reason != null) && reason.length() > 0) {
-			logger.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.INVALID_DEFAULTS, new Object[] {vt.getValuesAsString(), getID(), reason}));
+			logger.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.INVALID_DEFAULTS, new Object[] {vt.getValuesAsString(), getID(), reason}));
 			return;
 		}
 		String[] defaults = vt.getValuesAsArray();
@@ -277,20 +245,6 @@
 		_defaults = defaults;
 	}
 
-	/**
-	 * Method to set the validation value - min of AttributeDefinition.
-	 */
-	void setMinValue(Object minValue) {
-		this._minValue = minValue;
-	}
-
-	/**
-	 * Method to set the validation value - max of AttributeDefinition.
-	 */
-	void setMaxValue(Object maxValue) {
-		this._maxValue = maxValue;
-	}
-
 	/*
 	 * (non-Javadoc)
 	 * In order to be valid, a value must pass all of the following tests.
@@ -324,4 +278,198 @@
 	public String getMin() {
 		return _minValue == null ? null : String.valueOf(_minValue);
 	}
+
+	Object getMaxValue() {
+		return _maxValue;
+	}
+
+	Object getMinValue() {
+		return _minValue;
+	}
+
+	void getStrings(Set<String> strings) {
+		String[] curDefaults = _defaults;
+		if (curDefaults != null) {
+			for (String string : curDefaults) {
+				strings.add(string);
+			}
+		}
+		strings.add(_description);
+		strings.add(_id);
+		strings.add(_name);
+		strings.add(getLocalization());
+		for (String string : _values) {
+			strings.add(string);
+		}
+
+		for (String string : _labels) {
+			strings.add(string);
+		}
+		helper.getStrings(strings);
+		if (getType() == AttributeDefinition.STRING || getType() == AttributeDefinition.PASSWORD) {
+			if (_maxValue != null) {
+				strings.add(getMax());
+			}
+			if (_minValue != null) {
+				strings.add(getMin());
+			}
+		}
+	}
+
+	public static AttributeDefinitionImpl load(Reader reader, LogTracker logger) throws IOException {
+		String id = reader.readString();
+		String description = reader.readString();
+		String name = reader.readString();
+		int type = reader.readInt();
+		int cardinality = reader.readInt();
+		boolean isRequired = reader.readBoolean();
+		String localization = reader.readString();
+
+		String[] defaults = null;
+		if (reader.readBoolean()) {
+			int numDefaults = reader.readInt();
+			defaults = new String[numDefaults];
+			for (int i = 0; i < numDefaults; i++) {
+				defaults[i] = reader.readString();
+			}
+		}
+		int numLabels = reader.readInt();
+		ArrayList<String> labels = new ArrayList<>(numLabels);
+		for (int i = 0; i < numLabels; i++) {
+			labels.add(reader.readString());
+		}
+		int numValues = reader.readInt();
+		ArrayList<String> values = new ArrayList<>();
+		for (int i = 0; i < numValues; i++) {
+			values.add(reader.readString());
+		}
+		ExtendableHelper helper = ExtendableHelper.load(reader);
+		Object min = readMinMax(type, reader);
+		Object max = readMinMax(type, reader);
+
+		AttributeDefinitionImpl result = new AttributeDefinitionImpl(id, name, description, type, cardinality, min, max, isRequired, localization, logger, helper);
+		result.setDefaultValue(defaults);
+		result.setOption(labels, values, false);
+		return result;
+	}
+
+	public void write(Writer writer) throws IOException {
+		writer.writeString(_id);
+		writer.writeString(_description);
+		writer.writeString(_name);
+		writer.writeInt(_dataType);
+		writer.writeInt(_cardinality);
+		writer.writeBoolean(_isRequired);
+		writer.writeString(getLocalization());
+		String[] curDefaults = _defaults;
+		if (curDefaults == null) {
+			writer.writeBoolean(false);
+		} else {
+			writer.writeBoolean(true);
+			writer.writeInt(curDefaults.length);
+			for (String defaultValue : curDefaults) {
+				writer.writeString(defaultValue);
+			}
+		}
+		List<String> curLabels = _labels;
+		writer.writeInt(curLabels.size());
+		for (String label : curLabels) {
+			writer.writeString(label);
+		}
+		List<String> curValues = _values;
+		writer.writeInt(curValues.size());
+		for (String value : curValues) {
+			writer.writeString(value);
+		}
+		helper.write(writer);
+		writeMinMax(_minValue, writer);
+		writeMinMax(_maxValue, writer);
+	}
+
+	@SuppressWarnings("deprecation")
+	private static Object readMinMax(int dataType, Reader reader) throws IOException {
+		boolean isNull = reader.readBoolean();
+		if (isNull) {
+			return null;
+		}
+		switch (dataType) {
+			// PASSWORD should be treated like STRING.
+			case AttributeDefinition.PASSWORD :
+			case AttributeDefinition.STRING :
+				return reader.readString();
+			case AttributeDefinition.LONG :
+				return reader.readLong();
+			case AttributeDefinition.INTEGER :
+				return reader.readInt();
+			case AttributeDefinition.SHORT :
+				return reader.readShort();
+			case AttributeDefinition.CHARACTER :
+				return reader.readCharacter();
+			case AttributeDefinition.BYTE :
+				return reader.readByte();
+			case AttributeDefinition.DOUBLE :
+				return reader.readDouble();
+			case AttributeDefinition.FLOAT :
+				return reader.readFloat();
+			case AttributeDefinition.BIGINTEGER :
+				return new BigInteger(reader.readString());
+			case AttributeDefinition.BIGDECIMAL :
+				return new BigDecimal(reader.readString());
+			case AttributeDefinition.BOOLEAN :
+				return reader.readBoolean();
+			default :
+				return reader.readString();
+		}
+	}
+
+	@SuppressWarnings("deprecation")
+	private void writeMinMax(Object v, Writer writer) throws IOException {
+		if (v == null) {
+			writer.writeBoolean(true);
+			return;
+		}
+		writer.writeBoolean(false);
+		switch (_dataType) {
+			// PASSWORD should be treated like STRING.
+			case AttributeDefinition.PASSWORD :
+			case AttributeDefinition.STRING :
+				writer.writeString((String) v);
+				return;
+			case AttributeDefinition.LONG :
+				writer.writeLong((Long) v);
+				return;
+			case AttributeDefinition.INTEGER :
+				writer.writeInt((Integer) v);
+				return;
+			case AttributeDefinition.SHORT :
+				writer.writeShort((Short) v);
+				return;
+			case AttributeDefinition.CHARACTER :
+				writer.writeCharacter((Character) v);
+				return;
+			case AttributeDefinition.BYTE :
+				writer.writeByte((Byte) v);
+				return;
+			case AttributeDefinition.DOUBLE :
+				writer.writeDouble((Double) v);
+				return;
+			case AttributeDefinition.FLOAT :
+				writer.writeFloat((Float) v);
+				return;
+			case AttributeDefinition.BIGINTEGER :
+				writer.writeString(v.toString());
+				return;
+			case AttributeDefinition.BIGDECIMAL :
+				writer.writeString(v.toString());
+				return;
+			case AttributeDefinition.BOOLEAN :
+				writer.writeBoolean((Boolean) v);
+				return;
+			default :
+				// Unknown data type
+				writer.writeString(String.valueOf(v));
+				return;
+		}
+	}
+
 }
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/DataParser.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/DataParser.java
index 340740d..f0faf0e 100644
--- a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/DataParser.java
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/DataParser.java
@@ -21,7 +21,6 @@
 import javax.xml.parsers.SAXParser;
 import org.eclipse.osgi.util.NLS;
 import org.osgi.framework.Bundle;
-import org.osgi.service.log.LogService;
 import org.osgi.service.metatype.AttributeDefinition;
 import org.xml.sax.*;
 import org.xml.sax.helpers.DefaultHandler;
@@ -79,15 +78,15 @@
 	protected XMLReader _dp_xmlReader;
 
 	// DesignateHanders in DataParser class
-	Vector<DesignateHandler> _dp_designateHandlers = new Vector<DesignateHandler>(7);
+	List<DesignateHandler> _dp_designateHandlers = new ArrayList<>(7);
 	// ObjectClassDefinitions in DataParser class w/ corresponding reference keys
-	Hashtable<String, ObjectClassDefinitionImpl> _dp_OCDs = new Hashtable<String, ObjectClassDefinitionImpl>(7);
+	Map<String, ObjectClassDefinitionImpl> _dp_OCDs = new HashMap<>(7);
 	// Localization in DataParser class
 	String _dp_localization;
 
 	// Default visibility to avoid a plethora of synthetic accessor method warnings.
 	final LogTracker logger;
-	final Collection<Designate> designates = new ArrayList<Designate>(7);
+	final Collection<Designate> designates = new ArrayList<>(7);
 
 	/*
 	 * Constructor of class DataParser.
@@ -109,7 +108,7 @@
 		_dp_xmlReader.setErrorHandler(new MyErrorHandler(System.err));
 		InputStream is = _dp_url.openStream();
 		InputSource isource = new InputSource(is);
-		logger.log(LogService.LOG_DEBUG, "Starting to parse " + _dp_url); //$NON-NLS-1$					
+		logger.log(LogTracker.LOG_DEBUG, "Starting to parse " + _dp_url); //$NON-NLS-1$					
 		_dp_xmlReader.parse(isource);
 		return designates;
 	}
@@ -117,6 +116,7 @@
 	/*
 	 * Convert String for expected data type.
 	 */
+	@SuppressWarnings("deprecation")
 	static Object convert(String value, int type) {
 
 		if (value == null) {
@@ -225,13 +225,13 @@
 
 		public void startElement(String uri, String localName, String qName, Attributes attributes) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is AbstractHandler:startElement():" //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is AbstractHandler:startElement():" //$NON-NLS-1$
 					+ qName);
 			String name = getName(localName, qName);
 			if (name.equalsIgnoreCase(METADATA)) {
 				new MetaDataHandler(this).init(name, attributes);
 			} else {
-				logger.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.UNEXPECTED_ELEMENT, new Object[] {name, attributes.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.UNEXPECTED_ELEMENT, new Object[] {name, attributes.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 			}
 		}
 
@@ -251,7 +251,7 @@
 
 		public void init(String name, Attributes attributes) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is MetaDataHandler():init()"); //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is MetaDataHandler():init()"); //$NON-NLS-1$
 			super.init(name, attributes);
 			_dp_localization = attributes.getValue(LOCALIZATION);
 			if (_dp_localization == null) {
@@ -263,42 +263,39 @@
 
 		public void startElement(String uri, String localName, String qName, Attributes atts) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is MetaDataHandler:startElement():" //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is MetaDataHandler:startElement():" //$NON-NLS-1$
 					+ qName);
 			String name = getName(localName, qName);
 			if (name.equalsIgnoreCase(DESIGNATE)) {
 				DesignateHandler designateHandler = new DesignateHandler(this);
 				designateHandler.init(name, atts);
 				if (designateHandler._isParsedDataValid) {
-					_dp_designateHandlers.addElement(designateHandler);
+					_dp_designateHandlers.add(designateHandler);
 				}
 			} else if (name.equalsIgnoreCase(OCD)) {
 				OcdHandler ocdHandler = new OcdHandler(this);
 				ocdHandler.init(name, atts, _dp_OCDs);
 			} else {
-				logger.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.UNEXPECTED_ELEMENT, new Object[] {name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.UNEXPECTED_ELEMENT, new Object[] {name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 			}
 		}
 
 		protected void finished() {
 
-			logger.log(LogService.LOG_DEBUG, "Here is MetaDataHandler():finished()"); //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is MetaDataHandler():finished()"); //$NON-NLS-1$
 			if (_dp_designateHandlers.size() == 0) {
 				// Schema defines at least one DESIGNATE is required.
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.MISSING_ELEMENT, new Object[] {DESIGNATE, METADATA, elementId, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.MISSING_ELEMENT, new Object[] {DESIGNATE, METADATA, elementId, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
-			Enumeration<DesignateHandler> designateHandlerKeys = _dp_designateHandlers.elements();
-			while (designateHandlerKeys.hasMoreElements()) {
-				DesignateHandler dh = designateHandlerKeys.nextElement();
 
+			for (DesignateHandler dh : _dp_designateHandlers) {
 				ObjectClassDefinitionImpl ocd = _dp_OCDs.get(dh._ocdref);
 				if (ocd != null) {
 					designates.add(new Designate.Builder(ocd).bundle(dh._bundle_val).factoryPid(dh._factory_val).merge(dh._merge_val).pid(dh._pid_val).optional(dh._optional_val).build());
 				} else {
-					logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.OCD_REF_NOT_FOUND, new Object[] {dh._pid_val, dh._factory_val, dh._ocdref, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
-
+					logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.OCD_REF_NOT_FOUND, new Object[] {dh._pid_val, dh._factory_val, dh._ocdref, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				}
 			}
 		}
@@ -309,28 +306,28 @@
 	 */
 	private class OcdHandler extends AbstractHandler {
 
-		Hashtable<String, ObjectClassDefinitionImpl> _parent_OCDs_hashtable;
+		Map<String, ObjectClassDefinitionImpl> _parent_OCDs;
 		// This ID "_refID" is only used for reference by Designate element,
 		// not the PID or FPID of this OCD.
 		String _refID;
 		ObjectClassDefinitionImpl _ocd;
-		Vector<AttributeDefinitionImpl> _ad_vector = new Vector<AttributeDefinitionImpl>(7);
+		List<AttributeDefinitionImpl> _ads = new ArrayList<AttributeDefinitionImpl>(7);
 		List<Icon> icons = new ArrayList<Icon>(5);
 
 		public OcdHandler(ContentHandler handler) {
 			super(handler);
 		}
 
-		public void init(String name, Attributes atts, Hashtable<String, ObjectClassDefinitionImpl> ocds_hashtable) {
+		public void init(String name, Attributes atts, Map<String, ObjectClassDefinitionImpl> ocds_hashtable) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is OcdHandler():init()"); //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is OcdHandler():init()"); //$NON-NLS-1$
 			super.init(name, atts);
-			_parent_OCDs_hashtable = ocds_hashtable;
+			_parent_OCDs = ocds_hashtable;
 			collectExtensionAttributes(atts);
 			String ocd_name_val = atts.getValue(NAME);
 			if (ocd_name_val == null) {
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {NAME, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {NAME, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
 
@@ -342,7 +339,7 @@
 			_refID = atts.getValue(ID);
 			if (_refID == null) {
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {ID, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {ID, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
 
@@ -351,7 +348,7 @@
 
 		public void startElement(String uri, String localName, String qName, Attributes atts) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is OcdHandler:startElement():" //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is OcdHandler:startElement():" //$NON-NLS-1$
 					+ qName);
 			if (!_isParsedDataValid)
 				return;
@@ -359,29 +356,27 @@
 			String name = getName(localName, qName);
 			if (name.equalsIgnoreCase(AD)) {
 				AttributeDefinitionHandler attributeDefHandler = new AttributeDefinitionHandler(this);
-				attributeDefHandler.init(name, atts, _ad_vector);
+				attributeDefHandler.init(name, atts, _ads);
 			} else if (name.equalsIgnoreCase(ICON)) {
 				IconHandler iconHandler = new IconHandler(this);
 				iconHandler.init(name, atts);
 				if (iconHandler._isParsedDataValid)
 					icons.add(iconHandler._icon);
 			} else {
-				logger.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.UNEXPECTED_ELEMENT, new Object[] {name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.UNEXPECTED_ELEMENT, new Object[] {name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 			}
 		}
 
 		protected void finished() {
-			logger.log(LogService.LOG_DEBUG, "Here is OcdHandler():finished()"); //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is OcdHandler():finished()"); //$NON-NLS-1$
 			if (!_isParsedDataValid)
 				return;
 			// OCD gets all parsed ADs.
-			Enumeration<AttributeDefinitionImpl> adKey = _ad_vector.elements();
-			while (adKey.hasMoreElements()) {
-				AttributeDefinitionImpl ad = adKey.nextElement();
-				_ocd.addAttributeDefinition(ad, ad._isRequired);
+			for (AttributeDefinitionImpl ad : _ads) {
+				_ocd.addAttributeDefinition(ad, ad.isRequired());
 			}
 			_ocd.setIcons(icons);
-			_parent_OCDs_hashtable.put(_refID, _ocd);
+			_parent_OCDs.put(_refID, _ocd);
 		}
 	}
 
@@ -398,12 +393,12 @@
 
 		public void init(String name, Attributes atts) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is IconHandler:init()"); //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is IconHandler:init()"); //$NON-NLS-1$
 			super.init(name, atts);
 			String icon_resource_val = atts.getValue(RESOURCE);
 			if (icon_resource_val == null) {
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {RESOURCE, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {RESOURCE, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
 
@@ -427,9 +422,9 @@
 		AttributeDefinitionImpl _ad;
 		int _dataType;
 
-		Vector<AttributeDefinitionImpl> _parent_ADs_vector;
-		Vector<String> _optionLabel_vector = new Vector<String>(7);
-		Vector<String> _optionValue_vector = new Vector<String>(7);
+		List<AttributeDefinitionImpl> _parent_ADs;
+		ArrayList<String> _optionLabels = new ArrayList<>(7);
+		ArrayList<String> _optionValues = new ArrayList<>(7);
 
 		private String ad_defaults_str;
 
@@ -437,11 +432,11 @@
 			super(handler);
 		}
 
-		public void init(String name, Attributes atts, Vector<AttributeDefinitionImpl> ad_vector) {
+		public void init(String name, Attributes atts, List<AttributeDefinitionImpl> ads) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is AttributeDefinitionHandler():init()"); //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is AttributeDefinitionHandler():init()"); //$NON-NLS-1$
 			super.init(name, atts);
-			_parent_ADs_vector = ad_vector;
+			_parent_ADs = ads;
 			collectExtensionAttributes(atts);
 			String ad_name_val = atts.getValue(NAME);
 			if (ad_name_val == null) {
@@ -456,14 +451,14 @@
 			String ad_id_val = atts.getValue(ID);
 			if (ad_id_val == null) {
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {ID, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {ID, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
 
 			String ad_type_val = atts.getValue(TYPE);
 			if (ad_type_val == null) {
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {TYPE, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {TYPE, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
 			if (ad_type_val.equalsIgnoreCase(STRING)) {
@@ -488,7 +483,7 @@
 				_dataType = AttributeDefinition.PASSWORD;
 			} else {
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.INVALID_TYPE, new Object[] {ad_type_val, ad_id_val, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.INVALID_TYPE, new Object[] {ad_type_val, ad_id_val, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
 
@@ -528,7 +523,7 @@
 
 		public void startElement(String uri, String localName, String qName, Attributes atts) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is AttributeDefinitionHandler:startElement():" //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is AttributeDefinitionHandler:startElement():" //$NON-NLS-1$
 					+ qName);
 			if (!_isParsedDataValid)
 				return;
@@ -539,34 +534,34 @@
 				optionHandler.init(name, atts);
 				if (optionHandler._isParsedDataValid) {
 					// Only add valid Option
-					_optionLabel_vector.addElement(optionHandler._label_val);
-					_optionValue_vector.addElement(optionHandler._value_val);
+					_optionLabels.add(optionHandler._label_val);
+					_optionValues.add(optionHandler._value_val);
 				}
 			} else {
-				logger.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.UNEXPECTED_ELEMENT, new Object[] {name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.UNEXPECTED_ELEMENT, new Object[] {name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 			}
 		}
 
 		protected void finished() {
 
-			logger.log(LogService.LOG_DEBUG, "Here is AttributeDefinitionHandler():finished()"); //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is AttributeDefinitionHandler():finished()"); //$NON-NLS-1$
 			if (!_isParsedDataValid)
 				return;
-			int numOfValues = _optionValue_vector.size();
-			_ad.setOption(_optionLabel_vector, _optionValue_vector, true);
+			int numOfValues = _optionValues.size();
+			_ad.setOption(_optionLabels, _optionValues, true);
 			String[] values = _ad.getOptionValues();
 			if (values == null)
 				values = new String[0];
 			if (numOfValues != values.length)
-				logger.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.INVALID_OPTIONS_XML, new Object[] {elementId, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.INVALID_OPTIONS_XML, new Object[] {elementId, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 
 			if (ad_defaults_str != null) {
 				_ad.setDefaultValue(ad_defaults_str, true);
 				if (_ad.getDefaultValue() == null)
-					logger.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.INVALID_DEFAULTS_XML, new Object[] {ad_defaults_str, elementId, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+					logger.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.INVALID_DEFAULTS_XML, new Object[] {ad_defaults_str, elementId, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 			}
 
-			_parent_ADs_vector.addElement(_ad);
+			_parent_ADs.add(_ad);
 		}
 	}
 
@@ -584,68 +579,24 @@
 
 		public void init(String name, Attributes atts) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is OptionHandler:init()"); //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is OptionHandler:init()"); //$NON-NLS-1$
 			super.init(name, atts);
 			_label_val = atts.getValue(LABEL);
 			if (_label_val == null) {
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {LABEL, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {LABEL, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
 
 			_value_val = atts.getValue(VALUE);
 			if (_value_val == null) {
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {VALUE, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {VALUE, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
 		}
 	}
 
-	//	/**
-	//	 * Handler for the Simple Value element.
-	//	 */
-	//	private class SimpleValueHandler extends AbstractHandler {
-	//
-	//		StringBuffer	_buffer	= new StringBuffer();
-	//		Vector			_parent_value_vector;
-	//		String			_elementName;
-	//
-	//		public SimpleValueHandler(ContentHandler handler) {
-	//			super(handler);
-	//		}
-	//
-	//		public void init(String name, Attributes atts, Vector value_vector)
-	//				throws SAXException {
-	//
-	//			Logging.log(LogService.LOG_DEBUG,
-	//					"Here is SimpleValueHandler():init()"); //$NON-NLS-1$
-	//			_elementName = name;
-	//			_parent_value_vector = value_vector;
-	//		}
-	//
-	//		protected void finished() throws SAXException {
-	//
-	//			Logging.log(LogService.LOG_DEBUG,
-	//					"Here is SimpleValueHandler():finished()"); //$NON-NLS-1$
-	//			if (_parent_value_vector != null) {
-	//				_parent_value_vector.addElement(_buffer.toString());
-	//			}
-	//		}
-	//
-	//		public void characters(char buf[], int offset, int len)
-	//				throws SAXException {
-	//
-	//			Logging.log(LogService.LOG_DEBUG,
-	//					"Here is SimpleValueHandler(" //$NON-NLS-1$
-	//					+ _elementName
-	//					+ "):characters():[" //$NON-NLS-1$
-	//					+ new String(buf, offset, len)
-	//					+ "]"); //$NON-NLS-1$
-	//			_buffer.append(new String(buf, offset, len));
-	//		}
-	//	}
-
 	/**
 	 * Handler for the Designate element.
 	 */
@@ -665,13 +616,13 @@
 		}
 
 		public void init(String name, Attributes atts) {
-			logger.log(LogService.LOG_DEBUG, "Here is DesignateHandler():init()"); //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is DesignateHandler():init()"); //$NON-NLS-1$
 			super.init(name, atts);
 			_pid_val = atts.getValue(PID);
 			_factory_val = atts.getValue(FACTORY);
 			if (_pid_val == null && _factory_val == null) {
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_DESIGNATE_PID_AND_FACTORYPID, new Object[] {elementId, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_DESIGNATE_PID_AND_FACTORYPID, new Object[] {elementId, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
 
@@ -701,7 +652,7 @@
 
 		public void startElement(String uri, String localName, String qName, Attributes atts) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is DesignateHandler:startElement():" //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is DesignateHandler:startElement():" //$NON-NLS-1$
 					+ qName);
 			if (!_isParsedDataValid)
 				return;
@@ -714,20 +665,20 @@
 					_ocdref = objectHandler._ocdref;
 				}
 			} else {
-				logger.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.UNEXPECTED_ELEMENT, new Object[] {name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.UNEXPECTED_ELEMENT, new Object[] {name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 			}
 		}
 
 		protected void finished() {
 
-			logger.log(LogService.LOG_DEBUG, "Here is DesignateHandler():finished()"); //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is DesignateHandler():finished()"); //$NON-NLS-1$
 			if (!_isParsedDataValid)
 				return;
 
 			if (_ocdref == null) {
 				_isParsedDataValid = false;
 				// Schema defines at least one OBJECT is required.
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ELEMENT, new Object[] {OBJECT, DESIGNATE, elementId, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ELEMENT, new Object[] {OBJECT, DESIGNATE, elementId, _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 
 			}
@@ -747,19 +698,19 @@
 
 		public void init(String name, Attributes atts) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is ObjectHandler():init()"); //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is ObjectHandler():init()"); //$NON-NLS-1$
 			super.init(name, atts);
 			_ocdref = atts.getValue(OCDREF);
 			if (_ocdref == null) {
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {OCDREF, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {OCDREF, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
 		}
 
 		public void startElement(String uri, String localName, String qName, Attributes atts) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is ObjectHandler:startElement():" //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is ObjectHandler:startElement():" //$NON-NLS-1$
 					+ qName);
 			if (!_isParsedDataValid)
 				return;
@@ -770,7 +721,7 @@
 				attributeHandler.init(name, atts);
 				// The ATTRIBUTE element is only used by RFC94, do nothing for it here.
 			} else {
-				logger.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.UNEXPECTED_ELEMENT, new Object[] {name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.UNEXPECTED_ELEMENT, new Object[] {name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 			}
 		}
 	}
@@ -791,19 +742,19 @@
 
 		public void init(String name, Attributes atts) {
 
-			logger.log(LogService.LOG_DEBUG, "Here is AttributeHandler():init()"); //$NON-NLS-1$
+			logger.log(LogTracker.LOG_DEBUG, "Here is AttributeHandler():init()"); //$NON-NLS-1$
 			super.init(name, atts);
 			_adref_val = atts.getValue(ADREF);
 			if (_adref_val == null) {
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {ADREF, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {ADREF, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
 
 			_content_val = atts.getValue(CONTENT);
 			if (_content_val == null) {
 				_isParsedDataValid = false;
-				logger.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {CONTENT, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
+				logger.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.MISSING_ATTRIBUTE, new Object[] {CONTENT, name, atts.getValue(ID), _dp_url, _dp_bundle.getBundleId(), _dp_bundle.getSymbolicName()}));
 				return;
 			}
 		}
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/ExtendableHelper.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/ExtendableHelper.java
index 5bc9858..fc3d85d 100644
--- a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/ExtendableHelper.java
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/ExtendableHelper.java
@@ -13,28 +13,72 @@
  *******************************************************************************/
 package org.eclipse.equinox.metatype.impl;
 
+import java.io.IOException;
 import java.util.*;
+import java.util.Map.Entry;
 import org.eclipse.equinox.metatype.Extendable;
+import org.eclipse.equinox.metatype.impl.Persistence.Reader;
+import org.eclipse.equinox.metatype.impl.Persistence.Writer;
 
 public class ExtendableHelper implements Extendable {
-	private final Map<String, Map<String, String>> attributes;
+	private final Map<String, Map<String, String>> extensions;
 
 	public ExtendableHelper() {
 		this(Collections.<String, Map<String, String>> emptyMap());
 	}
 
-	public ExtendableHelper(Map<String, Map<String, String>> attributes) {
-		if (attributes == null)
+	public ExtendableHelper(Map<String, Map<String, String>> extensions) {
+		if (extensions == null)
 			throw new NullPointerException();
-		this.attributes = attributes;
+		this.extensions = extensions;
 	}
 
 	public Map<String, String> getExtensionAttributes(String schema) {
-		return Collections.unmodifiableMap(attributes.get(schema));
+		return Collections.unmodifiableMap(extensions.get(schema));
 	}
 
 	public Set<String> getExtensionUris() {
-		return Collections.unmodifiableSet(attributes.keySet());
+		return Collections.unmodifiableSet(extensions.keySet());
+	}
+
+	void getStrings(Set<String> strings) {
+		for (Entry<String, Map<String, String>> e1 : extensions.entrySet()) {
+			strings.add(e1.getKey());
+			for (Entry<String, String> e2 : e1.getValue().entrySet()) {
+				strings.add(e2.getKey());
+				strings.add(e2.getValue());
+			}
+		}
+	}
+
+	public static ExtendableHelper load(Reader reader) throws IOException {
+		Map<String, Map<String, String>> extensions = new HashMap<>();
+		int numExtensions = reader.readInt();
+		for (int i = 0; i < numExtensions; i++) {
+			String extKey = reader.readString();
+			int numAttrs = reader.readInt();
+			Map<String, String> extensionAttrs = new HashMap<>();
+			for (int j = 0; j < numAttrs; j++) {
+				String attrKey = reader.readString();
+				String attrValue = reader.readString();
+				extensionAttrs.put(attrKey, attrValue);
+			}
+			extensions.put(extKey, extensionAttrs);
+		}
+		return new ExtendableHelper(extensions);
+	}
+
+	public void write(Writer writer) throws IOException {
+		writer.writeInt(extensions.size());
+		for (Entry<String, Map<String, String>> extensionEntry : extensions.entrySet()) {
+			writer.writeString(extensionEntry.getKey());
+			Map<String, String> extensionAttrs = extensionEntry.getValue();
+			writer.writeInt(extensionAttrs.size());
+			for (Entry<String, String> attrs : extensionAttrs.entrySet()) {
+				writer.writeString(attrs.getKey());
+				writer.writeString(attrs.getValue());
+			}
+		}
 	}
 
 }
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/Icon.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/Icon.java
index a55d9c8..db7d514 100644
--- a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/Icon.java
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/Icon.java
@@ -13,6 +13,10 @@
  *******************************************************************************/
 package org.eclipse.equinox.metatype.impl;
 
+import java.io.IOException;
+import java.util.Set;
+import org.eclipse.equinox.metatype.impl.Persistence.Reader;
+import org.eclipse.equinox.metatype.impl.Persistence.Writer;
 import org.osgi.framework.Bundle;
 
 /**
@@ -21,13 +25,13 @@
 class Icon implements Cloneable {
 
 	private final String _fileName;
-	private final Integer _size;
+	private final int _size;
 	private final Bundle _bundle;
 
 	/**
 	 * Constructor of class Icon.
 	 */
-	public Icon(String fileName, Integer size, Bundle bundle) {
+	public Icon(String fileName, int size, Bundle bundle) {
 
 		this._fileName = fileName;
 		this._size = size;
@@ -60,4 +64,19 @@
 	Bundle getIconBundle() {
 		return _bundle;
 	}
+
+	void getStrings(Set<String> strings) {
+		strings.add(_fileName);
+	}
+
+	public static Icon load(Reader reader, Bundle b) throws IOException {
+		int size = reader.readInt();
+		String fileName = reader.readString();
+		return new Icon(fileName, size, b);
+	}
+
+	public void write(Writer writer) throws IOException {
+		writer.writeInt(_size);
+		writer.writeString(_fileName);
+	}
 }
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/LogTracker.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/LogTracker.java
index 041125e..8877eac 100644
--- a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/LogTracker.java
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/LogTracker.java
@@ -27,6 +27,19 @@
  */
 
 public class LogTracker extends ServiceTracker<LogService, LogService> {
+
+	@SuppressWarnings("deprecation")
+	final static int LOG_ERROR = LogService.LOG_ERROR;
+
+	@SuppressWarnings("deprecation")
+	final static int LOG_WARNING = LogService.LOG_WARNING;
+
+	@SuppressWarnings("deprecation")
+	final static int LOG_INFO = LogService.LOG_INFO;
+
+	@SuppressWarnings("deprecation")
+	final static int LOG_DEBUG = LogService.LOG_DEBUG;
+
 	/** LogService interface class name */
 	protected final static String clazz = "org.osgi.service.log.LogService"; //$NON-NLS-1$
 
@@ -63,7 +76,7 @@
 	}
 
 	@SuppressWarnings("deprecation")
-	public synchronized void log(ServiceReference<?> reference, int level, String message, Throwable exception) {
+	public void log(ServiceReference<?> reference, int level, String message, Throwable exception) {
 		ServiceReference<LogService>[] references = getServiceReferences();
 
 		if (references != null) {
@@ -94,7 +107,6 @@
 	 * @param throwable Log exception or null if none.
 	 * @param reference ServiceReference associated with message or null if none.
 	 */
-	@SuppressWarnings("deprecation")
 	protected void noLogService(int level, String message, Throwable throwable, ServiceReference<?> reference) {
 		if (out != null) {
 			synchronized (out) {
@@ -104,22 +116,22 @@
 				out.print(timestamp + " "); //$NON-NLS-1$
 
 				switch (level) {
-					case LogService.LOG_DEBUG : {
+					case LOG_DEBUG : {
 						out.print(LogTrackerMsg.Debug);
 
 						break;
 					}
-					case LogService.LOG_INFO : {
+					case LOG_INFO : {
 						out.print(LogTrackerMsg.Info);
 
 						break;
 					}
-					case LogService.LOG_WARNING : {
+					case LOG_WARNING : {
 						out.print(LogTrackerMsg.Warning);
 
 						break;
 					}
-					case LogService.LOG_ERROR : {
+					case LOG_ERROR : {
 						out.print(LogTrackerMsg.Error);
 
 						break;
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeInformationImpl.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeInformationImpl.java
index 67c9075..e045327 100644
--- a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeInformationImpl.java
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeInformationImpl.java
@@ -13,11 +13,14 @@
  *******************************************************************************/
 package org.eclipse.equinox.metatype.impl;
 
-import java.util.Enumeration;
-import java.util.Vector;
+import java.io.IOException;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Map.Entry;
 import javax.xml.parsers.SAXParser;
 import org.eclipse.equinox.metatype.EquinoxMetaTypeInformation;
-import org.osgi.framework.Bundle;
+import org.eclipse.equinox.metatype.impl.Persistence.Writer;
+import org.osgi.framework.*;
 
 /**
  * Implementation of MetaTypeProvider
@@ -30,6 +33,7 @@
  * <p>
  */
 public class MetaTypeInformationImpl extends MetaTypeProviderImpl implements EquinoxMetaTypeInformation {
+	static final String[] emptyStringArray = new String[0];
 
 	/**
 	 * Constructor of class MetaTypeInformationImpl.
@@ -38,6 +42,10 @@
 		super(bundle, parser, logger);
 	}
 
+	public MetaTypeInformationImpl(Bundle bundle, LogTracker logger, Map<String, ObjectClassDefinitionImpl> pidOCDs, Map<String, ObjectClassDefinitionImpl> fPidOCDs) {
+		super(bundle, logger, pidOCDs, fPidOCDs);
+	}
+
 	/*
 	 * (non-Javadoc)
 	 * 
@@ -45,19 +53,10 @@
 	 */
 	public String[] getPids() {
 
-		if (_allPidOCDs.size() == 0) {
-			return new String[0];
+		if (_allPidOCDs.isEmpty()) {
+			return emptyStringArray;
 		}
-
-		Vector<String> pids = new Vector<String>(7);
-		Enumeration<String> e = _allPidOCDs.keys();
-		while (e.hasMoreElements()) {
-			pids.addElement(e.nextElement());
-		}
-
-		String[] retvalue = new String[pids.size()];
-		pids.toArray(retvalue);
-		return retvalue;
+		return _allPidOCDs.keySet().toArray(emptyStringArray);
 	}
 
 	/*
@@ -66,17 +65,10 @@
 	 * @see org.osgi.service.metatype.MetaTypeInformation#getFactoryPids()
 	 */
 	public String[] getFactoryPids() {
-		if (_allFPidOCDs.size() == 0) {
-			return new String[0];
+		if (_allFPidOCDs.isEmpty()) {
+			return emptyStringArray;
 		}
-		Vector<String> fpids = new Vector<String>(7);
-		Enumeration<String> e = _allFPidOCDs.keys();
-		while (e.hasMoreElements()) {
-			fpids.addElement(e.nextElement());
-		}
-		String[] retvalue = new String[fpids.size()];
-		fpids.toArray(retvalue);
-		return retvalue;
+		return _allFPidOCDs.keySet().toArray(emptyStringArray);
 	}
 
 	/*
@@ -87,4 +79,54 @@
 	public Bundle getBundle() {
 		return this._bundle;
 	}
+
+	static MetaTypeInformationImpl load(BundleContext systemContext, LogTracker log, Persistence.Reader reader) throws IOException {
+		long id = reader.readLong();
+		Bundle b = systemContext.getBundle(id);
+		boolean valid = true;
+		if (b == null) {
+			valid = false;
+			// just use the system bundle for load purposes
+			b = systemContext.getBundle(Constants.SYSTEM_BUNDLE_LOCATION);
+		}
+
+		long lastModified = reader.readLong();
+		if (lastModified != b.getLastModified()) {
+			valid = false;
+		}
+		Map<String, ObjectClassDefinitionImpl> allPidOCDs = new HashMap<>();
+		int numPidOCDs = reader.readInt();
+		for (int i = 0; i < numPidOCDs; i++) {
+			String key = reader.readString();
+			ObjectClassDefinitionImpl ocd = ObjectClassDefinitionImpl.load(b, log, reader);
+			allPidOCDs.put(key, ocd);
+		}
+		Map<String, ObjectClassDefinitionImpl> allFPidOCDs = new HashMap<>();
+		int numFPidOCDs = reader.readInt();
+		for (int i = 0; i < numFPidOCDs; i++) {
+			String key = reader.readString();
+			ObjectClassDefinitionImpl ocd = ObjectClassDefinitionImpl.load(b, log, reader);
+			allFPidOCDs.put(key, ocd);
+		}
+
+		return !valid ? null : new MetaTypeInformationImpl(b, log, allPidOCDs, allFPidOCDs);
+	}
+
+	void write(Writer writer) throws IOException {
+		writer.writeLong(getBundle().getBundleId());
+		writer.writeLong(getBundle().getLastModified());
+
+		writer.writeInt(_allPidOCDs.size());
+		for (Entry<String, ObjectClassDefinitionImpl> entry : _allPidOCDs.entrySet()) {
+			writer.writeString(entry.getKey());
+			entry.getValue().write(writer);
+		}
+
+		writer.writeInt(_allFPidOCDs.size());
+		for (Entry<String, ObjectClassDefinitionImpl> entry : _allFPidOCDs.entrySet()) {
+			writer.writeString(entry.getKey());
+			entry.getValue().write(writer);
+		}
+	}
+
 }
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeProviderImpl.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeProviderImpl.java
index 58dfc50..fe33eaa 100644
--- a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeProviderImpl.java
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeProviderImpl.java
@@ -15,12 +15,12 @@
 
 import java.net.URL;
 import java.util.*;
+import java.util.Map.Entry;
 import javax.xml.parsers.SAXParser;
 import org.eclipse.equinox.metatype.EquinoxObjectClassDefinition;
 import org.eclipse.osgi.util.NLS;
 import org.osgi.framework.Bundle;
 import org.osgi.framework.Constants;
-import org.osgi.service.log.LogService;
 import org.osgi.service.metatype.MetaTypeProvider;
 import org.osgi.service.metatype.MetaTypeService;
 
@@ -38,13 +38,13 @@
 	public static final String RESOURCE_FILE_EXT = ".properties"; //$NON-NLS-1$
 	public static final char DIRECTORY_SEP = '/';
 
-	Bundle _bundle;
+	final Bundle _bundle;
 
-	Hashtable<String, ObjectClassDefinitionImpl> _allPidOCDs = new Hashtable<String, ObjectClassDefinitionImpl>(7);
-	Hashtable<String, ObjectClassDefinitionImpl> _allFPidOCDs = new Hashtable<String, ObjectClassDefinitionImpl>(7);
+	final Map<String, ObjectClassDefinitionImpl> _allPidOCDs;
+	final Map<String, ObjectClassDefinitionImpl> _allFPidOCDs;
 
 	String[] _locales;
-	boolean _isThereMeta = false;
+	final boolean _isThereMeta;
 
 	// Give access to subclasses.
 	protected final LogTracker logger;
@@ -56,15 +56,24 @@
 
 		this._bundle = bundle;
 		this.logger = logger;
-
+		this._allPidOCDs = new HashMap<>();
+		this._allFPidOCDs = new HashMap<>();
 		// read all bundle's metadata files and build internal data structures
 		_isThereMeta = readMetaFiles(bundle, parser);
 
 		if (!_isThereMeta) {
-			logger.log(LogService.LOG_DEBUG, NLS.bind(MetaTypeMsg.METADATA_NOT_FOUND, bundle.getSymbolicName(), bundle.getBundleId()));
+			logger.log(LogTracker.LOG_DEBUG, NLS.bind(MetaTypeMsg.METADATA_NOT_FOUND, bundle.getSymbolicName(), bundle.getBundleId()));
 		}
 	}
 
+	public MetaTypeProviderImpl(Bundle bundle, LogTracker logger, Map<String, ObjectClassDefinitionImpl> pidOCDs, Map<String, ObjectClassDefinitionImpl> fPidOCDs) {
+		this._bundle = bundle;
+		this.logger = logger;
+		this._isThereMeta = true;
+		this._allPidOCDs = pidOCDs;
+		this._allFPidOCDs = fPidOCDs;
+	}
+
 	/**
 	 * This method should do the following:
 	 * <p> - Obtain a SAX parser from the XML Parser Service:
@@ -107,7 +116,7 @@
 					}
 				}
 			} catch (Exception e) {
-				logger.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.METADATA_FILE_PARSE_ERROR, new Object[] {entry, bundle.getBundleId(), bundle.getSymbolicName()}), e);
+				logger.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.METADATA_FILE_PARSE_ERROR, new Object[] {entry, bundle.getBundleId(), bundle.getSymbolicName()}), e);
 			}
 		}
 		return result;
@@ -167,19 +176,15 @@
 	public synchronized String[] getLocales() {
 		if (_locales != null)
 			return checkForDefault(_locales);
-		Vector<String> localizationFiles = new Vector<String>(7);
+		List<String> localizationFiles = new ArrayList<String>(7);
 		// get all the localization resources for PIDS
-		Enumeration<ObjectClassDefinitionImpl> ocds = _allPidOCDs.elements();
-		while (ocds.hasMoreElements()) {
-			ObjectClassDefinitionImpl ocd = ocds.nextElement();
+		for (ObjectClassDefinitionImpl ocd : _allPidOCDs.values()) {
 			String localization = ocd.getLocalization();
 			if (localization != null && !localizationFiles.contains(localization))
 				localizationFiles.add(localization);
 		}
 		// get all the localization resources for FPIDS
-		ocds = _allFPidOCDs.elements();
-		while (ocds.hasMoreElements()) {
-			ObjectClassDefinitionImpl ocd = ocds.nextElement();
+		for (ObjectClassDefinitionImpl ocd : _allFPidOCDs.values()) {
 			String localization = ocd.getLocalization();
 			if (localization != null && !localizationFiles.contains(localization))
 				localizationFiles.add(localization);
@@ -187,9 +192,7 @@
 		if (localizationFiles.size() == 0)
 			localizationFiles.add(getBundleLocalization(_bundle));
 		Vector<String> locales = new Vector<String>(7);
-		Enumeration<String> eLocalizationFiles = localizationFiles.elements();
-		while (eLocalizationFiles.hasMoreElements()) {
-			String localizationFile = eLocalizationFiles.nextElement();
+		for (String localizationFile : localizationFiles) {
 			int iSlash = localizationFile.lastIndexOf(DIRECTORY_SEP);
 			String baseDir;
 			String baseFileName;
@@ -230,4 +233,15 @@
 			return null;
 		return locales;
 	}
+
+	void getStrings(Set<String> strings) {
+		for (Entry<String, ObjectClassDefinitionImpl> entry : _allPidOCDs.entrySet()) {
+			strings.add(entry.getKey());
+			entry.getValue().getStrings(strings);
+		}
+		for (Entry<String, ObjectClassDefinitionImpl> entry : _allFPidOCDs.entrySet()) {
+			strings.add(entry.getKey());
+			entry.getValue().getStrings(strings);
+		}
+	}
 }
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeProviderTracker.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeProviderTracker.java
index 77a922d..97f6624 100644
--- a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeProviderTracker.java
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeProviderTracker.java
@@ -22,7 +22,6 @@
 import org.osgi.framework.*;
 import org.osgi.service.cm.ManagedService;
 import org.osgi.service.cm.ManagedServiceFactory;
-import org.osgi.service.log.LogService;
 import org.osgi.service.metatype.*;
 import org.osgi.util.tracker.ServiceTracker;
 
@@ -158,7 +157,7 @@
 				e = ase;
 			}
 		}
-		log.log(LogService.LOG_WARNING, NLS.bind(MetaTypeMsg.INVALID_PID_METATYPE_PROVIDER_IGNORED, new Object[] {_bundle.getSymbolicName(), _bundle.getBundleId(), name, value}), e);
+		log.log(LogTracker.LOG_WARNING, NLS.bind(MetaTypeMsg.INVALID_PID_METATYPE_PROVIDER_IGNORED, new Object[] {_bundle.getSymbolicName(), _bundle.getBundleId(), name, value}), e);
 		return new String[0];
 	}
 
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeServiceImpl.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeServiceImpl.java
index 8d9c536..a87275e 100644
--- a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeServiceImpl.java
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/MetaTypeServiceImpl.java
@@ -13,15 +13,18 @@
  *******************************************************************************/
 package org.eclipse.equinox.metatype.impl;
 
+import java.io.*;
 import java.security.AccessController;
 import java.security.PrivilegedAction;
-import java.util.Hashtable;
+import java.util.*;
 import javax.xml.parsers.*;
 import org.eclipse.equinox.metatype.EquinoxMetaTypeInformation;
 import org.eclipse.equinox.metatype.EquinoxMetaTypeService;
+import org.eclipse.equinox.metatype.impl.Persistence.Reader;
+import org.eclipse.equinox.metatype.impl.Persistence.Writer;
 import org.eclipse.osgi.util.NLS;
 import org.osgi.framework.*;
-import org.osgi.service.log.LogService;
+import org.osgi.service.metatype.MetaTypeInformation;
 import org.osgi.util.tracker.ServiceTracker;
 import org.xml.sax.SAXException;
 
@@ -29,7 +32,7 @@
  * Implementation of MetaTypeService
  */
 public class MetaTypeServiceImpl implements EquinoxMetaTypeService, SynchronousBundleListener {
-
+	private static String CACHE_FILE = "metaTypeCache"; //$NON-NLS-1$
 	SAXParserFactory _parserFactory;
 	private Hashtable<Long, EquinoxMetaTypeInformation> _mtps = new Hashtable<Long, EquinoxMetaTypeInformation>(7);
 
@@ -71,7 +74,7 @@
 					try {
 						impl = new MetaTypeInformationImpl(b, newParser(), loggerTemp);
 					} catch (Exception e) {
-						loggerTemp.log(LogService.LOG_ERROR, NLS.bind(MetaTypeMsg.METADATA_PARSE_ERROR, b.getBundleId(), b.getSymbolicName()), e);
+						loggerTemp.log(LogTracker.LOG_ERROR, NLS.bind(MetaTypeMsg.METADATA_PARSE_ERROR, b.getBundleId(), b.getSymbolicName()), e);
 					}
 					if (impl == null || !impl._isThereMeta)
 						return new MetaTypeProviderTracker(b, loggerTemp, tracker);
@@ -135,4 +138,66 @@
 				break;
 		}
 	}
+
+	void load(BundleContext context, LogTracker log, ServiceTracker<Object, Object> tracker) throws IOException {
+		File cache = context.getDataFile(CACHE_FILE);
+		// using system context to see all bundles by the ID
+		BundleContext systemContext = context.getBundle(Constants.SYSTEM_BUNDLE_LOCATION).getBundleContext();
+		if (cache.isFile()) {
+			try (Reader reader = new Reader(new DataInputStream(new BufferedInputStream(new FileInputStream(cache))))) {
+
+				int numService = reader.readInt();
+				for (int i = 0; i < numService; i++) {
+					long id = reader.readLong();
+					Bundle b = systemContext.getBundle(id);
+					if (b != null) {
+						_mtps.put(b.getBundleId(), new MetaTypeProviderTracker(b, log, tracker));
+					}
+				}
+
+				reader.readIndexedStrings();
+
+				int numXML = reader.readInt();
+				for (int i = 0; i < numXML; i++) {
+					MetaTypeInformationImpl info = MetaTypeInformationImpl.load(systemContext, log, reader);
+					if (info != null) {
+						_mtps.put(info.getBundle().getBundleId(), info);
+					}
+				}
+			}
+		}
+	}
+
+	void save(BundleContext context) throws IOException {
+		File cache = context.getDataFile(CACHE_FILE);
+		try (Writer writer = new Writer(new DataOutputStream(new BufferedOutputStream(new FileOutputStream(cache))))) {
+			List<MetaTypeInformation> serviceInfos = new ArrayList<>();
+			List<MetaTypeInformationImpl> xmlInfos = new ArrayList<>();
+			synchronized (_mtps) {
+				for (MetaTypeInformation info : _mtps.values()) {
+					if (info instanceof MetaTypeInformationImpl) {
+						xmlInfos.add((MetaTypeInformationImpl) info);
+					} else {
+						serviceInfos.add(info);
+					}
+				}
+			}
+
+			writer.writeInt(serviceInfos.size());
+			for (MetaTypeInformation info : serviceInfos) {
+				writer.writeLong(info.getBundle().getBundleId());
+			}
+
+			Set<String> strings = new HashSet<>();
+			for (MetaTypeInformationImpl info : xmlInfos) {
+				info.getStrings(strings);
+			}
+			writer.writeIndexedStrings(strings);
+
+			writer.writeInt(xmlInfos.size());
+			for (MetaTypeInformationImpl info : xmlInfos) {
+				info.write(writer);
+			}
+		}
+	}
 }
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/ObjectClassDefinitionImpl.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/ObjectClassDefinitionImpl.java
index f5907d0..a4636fb 100644
--- a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/ObjectClassDefinitionImpl.java
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/ObjectClassDefinitionImpl.java
@@ -19,6 +19,7 @@
 import java.util.*;
 import org.eclipse.equinox.metatype.EquinoxAttributeDefinition;
 import org.eclipse.equinox.metatype.EquinoxObjectClassDefinition;
+import org.eclipse.equinox.metatype.impl.Persistence.Writer;
 import org.osgi.framework.Bundle;
 
 /**
@@ -35,12 +36,11 @@
 	private final String _id;
 	private final String _description;
 	private final int _type;
-	private final Vector<AttributeDefinitionImpl> _required = new Vector<AttributeDefinitionImpl>(7);
-	private final Vector<AttributeDefinitionImpl> _optional = new Vector<AttributeDefinitionImpl>(7);
+	private final List<AttributeDefinitionImpl> _required = new ArrayList<>(7);
+	private final List<AttributeDefinitionImpl> _optional = new ArrayList<>(7);
 	private final ExtendableHelper helper;
 
-	// @GuardedBy("this")
-	private List<Icon> icons;
+	private volatile List<Icon> icons = null;
 
 	/*
 	 * Constructor of class ObjectClassDefinitionImpl.
@@ -64,19 +64,18 @@
 	/*
 	 * 
 	 */
-	public synchronized Object clone() {
+	public Object clone() {
 
 		ObjectClassDefinitionImpl ocd = new ObjectClassDefinitionImpl(_name, _description, _id, _type, getLocalization(), helper);
-		for (int i = 0; i < _required.size(); i++) {
-			AttributeDefinitionImpl ad = _required.elementAt(i);
+		for (AttributeDefinitionImpl ad : _required) {
 			ocd.addAttributeDefinition((AttributeDefinitionImpl) ad.clone(), true);
 		}
-		for (int i = 0; i < _optional.size(); i++) {
-			AttributeDefinitionImpl ad = _optional.elementAt(i);
+		for (AttributeDefinitionImpl ad : _optional) {
 			ocd.addAttributeDefinition((AttributeDefinitionImpl) ad.clone(), false);
 		}
-		if (icons != null)
+		if (icons != null) {
 			ocd.setIcons(new ArrayList<Icon>(icons));
+		}
 		return ocd;
 	}
 
@@ -127,15 +126,13 @@
 			case ALL :
 			default :
 				atts = new EquinoxAttributeDefinition[_required.size() + _optional.size()];
-				Enumeration<AttributeDefinitionImpl> e = _required.elements();
 				int i = 0;
-				while (e.hasMoreElements()) {
-					atts[i] = e.nextElement();
+				for (AttributeDefinitionImpl attr : _required) {
+					atts[i] = attr;
 					i++;
 				}
-				e = _optional.elements();
-				while (e.hasMoreElements()) {
-					atts[i] = e.nextElement();
+				for (AttributeDefinitionImpl attr : _optional) {
+					atts[i] = attr;
 					i++;
 				}
 				return atts;
@@ -148,9 +145,9 @@
 	void addAttributeDefinition(AttributeDefinitionImpl ad, boolean isRequired) {
 
 		if (isRequired) {
-			_required.addElement(ad);
+			_required.add(ad);
 		} else {
-			_optional.addElement(ad);
+			_optional.add(ad);
 		}
 	}
 
@@ -159,7 +156,7 @@
 	 * 
 	 * @see org.osgi.service.metatype.ObjectClassDefinition#getIcon(int)
 	 */
-	public synchronized InputStream getIcon(int sizeHint) throws IOException {
+	public InputStream getIcon(int sizeHint) throws IOException {
 		// The parameter simply represents a requested size. This method should never return null if an
 		// icon exists.
 		// Temporary icon to hold the requested size for use in binary search comparator.
@@ -206,7 +203,7 @@
 		return null;
 	}
 
-	synchronized void setIcons(List<Icon> icons) {
+	void setIcons(List<Icon> icons) {
 		// Do nothing if icons is null or empty.
 		if (icons == null || icons.isEmpty())
 			return;
@@ -222,15 +219,10 @@
 	 */
 	void setResourceBundle(String assignedLocale, Bundle bundle) {
 		setLocaleAndBundle(assignedLocale, bundle);
-		Enumeration<AttributeDefinitionImpl> allADReqs = _required.elements();
-		while (allADReqs.hasMoreElements()) {
-			AttributeDefinitionImpl ad = allADReqs.nextElement();
+		for (AttributeDefinitionImpl ad : _required) {
 			ad.setLocaleAndBundle(assignedLocale, bundle);
 		}
-
-		Enumeration<AttributeDefinitionImpl> allADOpts = _optional.elements();
-		while (allADOpts.hasMoreElements()) {
-			AttributeDefinitionImpl ad = allADOpts.nextElement();
+		for (AttributeDefinitionImpl ad : _optional) {
 			ad.setLocaleAndBundle(assignedLocale, bundle);
 		}
 	}
@@ -242,4 +234,74 @@
 	public Set<String> getExtensionUris() {
 		return helper.getExtensionUris();
 	}
+
+	void getStrings(Set<String> strings) {
+		helper.getStrings(strings);
+		strings.add(_description);
+		strings.add(_id);
+		strings.add(_name);
+		strings.add(getLocalization());
+		@SuppressWarnings("hiding")
+		List<Icon> icons = this.icons;
+		if (icons != null) {
+			for (Icon icon : icons) {
+				icon.getStrings(strings);
+			}
+		}
+	}
+
+	static ObjectClassDefinitionImpl load(Bundle b, LogTracker logger, Persistence.Reader reader) throws IOException {
+		String description = reader.readString();
+		String id = reader.readString();
+		String name = reader.readString();
+		int type = reader.readInt();
+		String localization = reader.readString();
+		ExtendableHelper helper = ExtendableHelper.load(reader);
+		ObjectClassDefinitionImpl result = new ObjectClassDefinitionImpl(name, description, id, type, localization, helper);
+
+		int numIcons = reader.readInt();
+		List<Icon> icons = null;
+		if (numIcons > 0) {
+			icons = new ArrayList<>(numIcons);
+			for (int i = 0; i < numIcons; i++) {
+				icons.add(Icon.load(reader, b));
+			}
+		}
+		result.setIcons(icons);
+
+		int numRequired = reader.readInt();
+		for (int i = 0; i < numRequired; i++) {
+			result.addAttributeDefinition(AttributeDefinitionImpl.load(reader, logger), true);
+		}
+		int numOptional = reader.readInt();
+		for (int i = 0; i < numOptional; i++) {
+			result.addAttributeDefinition(AttributeDefinitionImpl.load(reader, logger), false);
+		}
+
+		return result;
+	}
+
+	void write(Writer writer) throws IOException {
+		writer.writeString(_description);
+		writer.writeString(_id);
+		writer.writeString(_name);
+		writer.writeInt(_type);
+		writer.writeString(getLocalization());
+		helper.write(writer);
+		List<Icon> curIcons = this.icons;
+		writer.writeInt(curIcons == null ? 0 : curIcons.size());
+		if (curIcons != null) {
+			for (Icon icon : curIcons) {
+				icon.write(writer);
+			}
+		}
+		writer.writeInt(_required.size());
+		for (AttributeDefinitionImpl ad : _required) {
+			ad.write(writer);
+		}
+		writer.writeInt(_optional.size());
+		for (AttributeDefinitionImpl ad : _optional) {
+			ad.write(writer);
+		}
+	}
 }
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/Persistence.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/Persistence.java
new file mode 100644
index 0000000..da3212b
--- /dev/null
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/Persistence.java
@@ -0,0 +1,206 @@
+package org.eclipse.equinox.metatype.impl;
+
+import java.io.*;
+import java.util.*;
+
+/*******************************************************************************
+ * Copyright (c) 2019 IBM Corporation.
+ *
+ * This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License 2.0
+ * which accompanies this distribution, and is available at
+ * https://www.eclipse.org/legal/epl-2.0/
+ *
+ * SPDX-License-Identifier: EPL-2.0
+ *
+ * Contributors:
+ *     IBM Corporation - initial API and implementation
+ *******************************************************************************/
+
+public class Persistence {
+
+	private static final String UTF_8 = "UTF-8"; //$NON-NLS-1$
+	private static final byte NULL = 0;
+	private static final byte OBJECT = 1;
+	private static final byte INDEX = 2;
+	private static final byte LONG_STRING = 3;
+
+	private Persistence() {
+	}
+
+	public static class Reader implements Closeable {
+		private final Map<Integer, String> readStringCache = new HashMap<>();
+		private final DataInputStream in;
+
+		public Reader(DataInputStream in) {
+			this.in = in;
+		}
+
+		public void readIndexedStrings() throws IOException {
+			int num = in.readInt();
+			for (int i = 0; i < num; i++) {
+				readIndexedString();
+			}
+		}
+
+		private String readIndexedString() throws IOException {
+			String string = readString();
+			readStringCache.put(Integer.valueOf(in.readInt()), string);
+			return string;
+		}
+
+		public String readString() throws IOException {
+			byte type = in.readByte();
+			if (type == INDEX) {
+				int index = in.readInt();
+				return readStringCache.get(index);
+			}
+			if (type == NULL) {
+				return null;
+			}
+			String string;
+			if (type == LONG_STRING) {
+				int length = in.readInt();
+				byte[] data = new byte[length];
+				in.readFully(data);
+				string = new String(data, UTF_8);
+			} else {
+				string = in.readUTF();
+			}
+
+			return string;
+		}
+
+		public long readLong() throws IOException {
+			return in.readLong();
+		}
+
+		public int readInt() throws IOException {
+			return in.readInt();
+		}
+
+		@Override
+		public void close() throws IOException {
+			in.close();
+		}
+
+		public boolean readBoolean() throws IOException {
+			return in.readBoolean();
+		}
+
+		public short readShort() throws IOException {
+			return in.readShort();
+		}
+
+		public char readCharacter() throws IOException {
+			return in.readChar();
+		}
+
+		public byte readByte() throws IOException {
+			return in.readByte();
+		}
+
+		public double readDouble() throws IOException {
+			return readDouble();
+		}
+
+		public float readFloat() throws IOException {
+			return in.readFloat();
+		}
+	}
+
+	public static class Writer implements Closeable {
+		private final Map<String, Integer> writeStringCache = new HashMap<>();
+		private final DataOutputStream out;
+
+		public Writer(DataOutputStream out) {
+			this.out = out;
+		}
+
+		public void writeIndexedStrings(Set<String> strings) throws IOException {
+			strings.remove(null); // do not index null
+			out.writeInt(strings.size());
+			for (String string : strings) {
+				writeIndexedString(string);
+			}
+		}
+
+		private void writeIndexedString(String string) throws IOException {
+			writeString(string);
+			addToIndex(string);
+		}
+
+		public void writeString(String string) throws IOException {
+			Integer index = string != null ? writeStringCache.get(string) : null;
+			if (index != null) {
+				out.writeByte(INDEX);
+				out.writeInt(index);
+				return;
+			}
+
+			if (string == null)
+				out.writeByte(NULL);
+			else {
+				byte[] data = string.getBytes(UTF_8);
+
+				if (data.length > 65535) {
+					out.writeByte(LONG_STRING);
+					out.writeInt(data.length);
+					out.write(data);
+				} else {
+					out.writeByte(OBJECT);
+					out.writeUTF(string);
+				}
+			}
+		}
+
+		private void addToIndex(String string) throws IOException {
+			if (string == null) {
+				throw new NullPointerException();
+			}
+			Integer cur = writeStringCache.get(string);
+			if (cur != null)
+				throw new IllegalStateException("String is already in the write table: " + string); //$NON-NLS-1$
+			Integer index = writeStringCache.size();
+			writeStringCache.put(string, index);
+			out.writeInt(index.intValue());
+		}
+
+		@Override
+		public void close() throws IOException {
+			out.close();
+		}
+
+		public void writeInt(int v) throws IOException {
+			out.writeInt(v);
+		}
+
+		public void writeLong(long v) throws IOException {
+			out.writeLong(v);
+		}
+
+		public void writeBoolean(boolean v) throws IOException {
+			out.writeBoolean(v);
+		}
+
+		public void writeShort(Short v) throws IOException {
+			out.writeShort(v);
+		}
+
+		public void writeCharacter(Character v) throws IOException {
+			out.writeChar(v);
+		}
+
+		public void writeByte(Byte v) throws IOException {
+			out.writeByte(v);
+		}
+
+		public void writeDouble(Double v) throws IOException {
+			out.writeDouble(v);
+		}
+
+		public void writeFloat(Float v) throws IOException {
+			out.writeFloat(v);
+		}
+	}
+}
diff --git a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/ValueTokenizer.java b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/ValueTokenizer.java
index ef6f2fd..014eb50 100644
--- a/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/ValueTokenizer.java
+++ b/bundles/org.eclipse.equinox.metatype/src/org/eclipse/equinox/metatype/impl/ValueTokenizer.java
@@ -17,7 +17,6 @@
 import java.math.BigInteger;
 import java.util.*;
 import org.eclipse.osgi.util.NLS;
-import org.osgi.service.log.LogService;
 import org.osgi.service.metatype.AttributeDefinition;
 
 public class ValueTokenizer {
@@ -114,7 +113,7 @@
 	}
 
 	/*
-	 * Method to return values as Vector.
+	 * Method to return values as collection.
 	 */
 	public Collection<String> getValues() {
 		return Collections.unmodifiableList(values);
@@ -150,20 +149,21 @@
 		try {
 			// All or nothing. If either min or max is not null and cannot be
 			// parsed as an integer, do the string comparison instead.
-			Integer min = ad._minValue == null ? null : Integer.valueOf((String) ad._minValue);
-			Integer max = ad._maxValue == null ? null : Integer.valueOf((String) ad._maxValue);
+			Integer min = ad.getMinValue() == null ? null : Integer.valueOf((String) ad.getMinValue());
+			Integer max = ad.getMaxValue() == null ? null : Integer.valueOf((String) ad.getMaxValue());
 			if (min != null && value.length() < min)
 				return true;
 			if (max != null && value.length() > max)
 				return true;
 		} catch (NumberFormatException e) {
 			// Either min or max was not an integer. Do a string comparison.
-			if ((ad._minValue != null && value.compareTo((String) ad._minValue) < 0) || (ad._maxValue != null && value.compareTo((String) ad._maxValue) > 0))
+			if ((ad.getMinValue() != null && value.compareTo((String) ad.getMinValue()) < 0) || (ad.getMaxValue() != null && value.compareTo((String) ad.getMaxValue()) > 0))
 				return true;
 		}
 		return false;
 	}
 
+	@SuppressWarnings("deprecation")
 	public String validate(AttributeDefinitionImpl ad) {
 		// An empty list means the original value was null. Null is never valid.
 		if (values.isEmpty()) {
@@ -187,37 +187,37 @@
 			for (Iterator<String> i = values.iterator(); i.hasNext();) {
 				s = i.next();
 				// If options were declared and the value does not match one of them, the value is not valid.
-				if (!ad._values.isEmpty() && !ad._values.contains(s)) {
+				if (ad.containsInvalidValue(s)) {
 					return NLS.bind(MetaTypeMsg.VALUE_OUT_OF_OPTION, s);
 				}
 				// Check the type. Also check the range if min or max were declared.
 				boolean rangeError = false;
-				switch (ad._dataType) {
+				switch (ad.getType()) {
 					case AttributeDefinition.PASSWORD :
 					case AttributeDefinition.STRING :
 						rangeError = validateString(ad, s);
 						break;
 					case AttributeDefinition.INTEGER :
 						Integer intVal = Integer.valueOf(s);
-						if (ad._minValue != null && intVal.compareTo((Integer) ad._minValue) < 0) {
+						if (ad.getMinValue() != null && intVal.compareTo((Integer) ad.getMinValue()) < 0) {
 							rangeError = true;
-						} else if (ad._maxValue != null && intVal.compareTo((Integer) ad._maxValue) > 0) {
+						} else if (ad.getMaxValue() != null && intVal.compareTo((Integer) ad.getMaxValue()) > 0) {
 							rangeError = true;
 						}
 						break;
 					case AttributeDefinition.LONG :
 						Long longVal = Long.valueOf(s);
-						if (ad._minValue != null && longVal.compareTo((Long) ad._minValue) < 0) {
+						if (ad.getMinValue() != null && longVal.compareTo((Long) ad.getMinValue()) < 0) {
 							rangeError = true;
-						} else if (ad._maxValue != null && longVal.compareTo((Long) ad._maxValue) > 0) {
+						} else if (ad.getMaxValue() != null && longVal.compareTo((Long) ad.getMaxValue()) > 0) {
 							rangeError = true;
 						}
 						break;
 					case AttributeDefinition.DOUBLE :
 						Double doubleVal = Double.valueOf(s);
-						if (ad._minValue != null && doubleVal.compareTo((Double) ad._minValue) < 0) {
+						if (ad.getMinValue() != null && doubleVal.compareTo((Double) ad.getMinValue()) < 0) {
 							rangeError = true;
-						} else if (ad._maxValue != null && doubleVal.compareTo((Double) ad._maxValue) > 0) {
+						} else if (ad.getMaxValue() != null && doubleVal.compareTo((Double) ad.getMaxValue()) > 0) {
 							rangeError = true;
 						}
 						break;
@@ -227,49 +227,49 @@
 						break;
 					case AttributeDefinition.CHARACTER :
 						Character charVal = Character.valueOf(s.charAt(0));
-						if (ad._minValue != null && charVal.compareTo((Character) ad._minValue) < 0) {
+						if (ad.getMinValue() != null && charVal.compareTo((Character) ad.getMinValue()) < 0) {
 							rangeError = true;
-						} else if (ad._maxValue != null && charVal.compareTo((Character) ad._maxValue) > 0) {
+						} else if (ad.getMaxValue() != null && charVal.compareTo((Character) ad.getMaxValue()) > 0) {
 							rangeError = true;
 						}
 						break;
 					case AttributeDefinition.FLOAT :
 						Float floatVal = Float.valueOf(s);
-						if (ad._minValue != null && floatVal.compareTo((Float) ad._minValue) < 0) {
+						if (ad.getMinValue() != null && floatVal.compareTo((Float) ad.getMinValue()) < 0) {
 							rangeError = true;
-						} else if (ad._maxValue != null && floatVal.compareTo((Float) ad._maxValue) > 0) {
+						} else if (ad.getMaxValue() != null && floatVal.compareTo((Float) ad.getMaxValue()) > 0) {
 							rangeError = true;
 						}
 						break;
 					case AttributeDefinition.SHORT :
 						Short shortVal = Short.valueOf(s);
-						if (ad._minValue != null && shortVal.compareTo((Short) ad._minValue) < 0) {
+						if (ad.getMinValue() != null && shortVal.compareTo((Short) ad.getMinValue()) < 0) {
 							rangeError = true;
-						} else if (ad._maxValue != null && shortVal.compareTo((Short) ad._maxValue) > 0) {
+						} else if (ad.getMaxValue() != null && shortVal.compareTo((Short) ad.getMaxValue()) > 0) {
 							rangeError = true;
 						}
 						break;
 					case AttributeDefinition.BYTE :
 						Byte byteVal = Byte.valueOf(s);
-						if (ad._minValue != null && byteVal.compareTo((Byte) ad._minValue) < 0) {
+						if (ad.getMinValue() != null && byteVal.compareTo((Byte) ad.getMinValue()) < 0) {
 							rangeError = true;
-						} else if (ad._maxValue != null && byteVal.compareTo((Byte) ad._maxValue) > 0) {
+						} else if (ad.getMaxValue() != null && byteVal.compareTo((Byte) ad.getMaxValue()) > 0) {
 							rangeError = true;
 						}
 						break;
 					case AttributeDefinition.BIGDECIMAL :
 						BigDecimal bigDecVal = new BigDecimal(s);
-						if (ad._minValue != null && bigDecVal.compareTo((BigDecimal) ad._minValue) < 0) {
+						if (ad.getMinValue() != null && bigDecVal.compareTo((BigDecimal) ad.getMinValue()) < 0) {
 							rangeError = true;
-						} else if (ad._maxValue != null && bigDecVal.compareTo((BigDecimal) ad._maxValue) > 0) {
+						} else if (ad.getMaxValue() != null && bigDecVal.compareTo((BigDecimal) ad.getMaxValue()) > 0) {
 							rangeError = true;
 						}
 						break;
 					case AttributeDefinition.BIGINTEGER :
 						BigInteger bigIntVal = new BigInteger(s);
-						if (ad._minValue != null && bigIntVal.compareTo((BigInteger) ad._minValue) < 0) {
+						if (ad.getMinValue() != null && bigIntVal.compareTo((BigInteger) ad.getMinValue()) < 0) {
 							rangeError = true;
-						} else if (ad._maxValue != null && bigIntVal.compareTo((BigInteger) ad._maxValue) > 0) {
+						} else if (ad.getMaxValue() != null && bigIntVal.compareTo((BigInteger) ad.getMaxValue()) > 0) {
 							rangeError = true;
 						}
 						break;
@@ -286,7 +286,7 @@
 			return NLS.bind(MetaTypeMsg.VALUE_NOT_A_NUMBER, s);
 		} catch (Exception e) {
 			String message = NLS.bind(MetaTypeMsg.EXCEPTION_MESSAGE, e.getClass().getName(), e.getMessage());
-			logger.log(LogService.LOG_DEBUG, message, e);
+			logger.log(LogTracker.LOG_DEBUG, message, e);
 			return message;
 		}
 	}