[167482] Move to binary publish file
diff --git a/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/ModulePublishInfo.java b/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/ModulePublishInfo.java
index 6998a48..c3d4afc 100644
--- a/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/ModulePublishInfo.java
+++ b/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/ModulePublishInfo.java
@@ -10,6 +10,9 @@
  **********************************************************************/
 package org.eclipse.wst.server.core.internal;
 
+import java.io.DataInput;
+import java.io.DataOutput;
+import java.io.IOException;
 import java.util.*;
 import org.eclipse.core.runtime.*;
 import org.eclipse.wst.server.core.IModule;
@@ -67,6 +70,18 @@
 		load(memento);
 	}
 
+	/**
+	 * ModulePublishInfo constructor.
+	 * 
+	 * @param in an input stream
+	 * @throws IOException if the load fails
+	 */
+	public ModulePublishInfo(DataInput in) throws IOException {
+		super();
+		
+		load(in);
+	}
+
 	public String getModuleId() {
 		return moduleId;
 	}
@@ -88,7 +103,7 @@
 	}
 
 	/**
-	 * 
+	 * Used only for reading from WTP 1.x workspaces.
 	 */
 	protected void load(IMemento memento) {
 		Trace.trace(Trace.FINEST, "Loading module publish info for: " + memento);
@@ -107,6 +122,9 @@
 		}
 	}
 
+	/**
+	 * Used only for reading from WTP 1.x workspaces.
+	 */
 	protected IModuleResource[] loadResource(IMemento memento, IPath path) {
 		if (memento == null)
 			return new IModuleResource[0];
@@ -142,42 +160,89 @@
 		return resources2;
 	}
 
-	/**
-	 * 
-	 */
-	protected void save(IMemento memento) {
+	protected void load(DataInput in) throws IOException {
+		Trace.trace(Trace.FINEST, "Loading module publish info");
+		
+		moduleId = in.readUTF();
+		byte b = in.readByte();
+		
+		if ((b & 1) != 0)
+			name = in.readUTF();
+		else
+			name = null;
+		
+		if ((b & 2) != 0) {
+			String mt = in.readUTF();
+			String mv = in.readUTF();
+			if (mt != null && mt.length() > 0)
+				moduleType = new ModuleType(mt, mv);
+		} else
+			moduleType = null;
+		
+		resources = loadResource(in, new Path(""));
+	}
+
+	private IModuleResource[] loadResource(DataInput in, IPath path) throws IOException {
+		int size = in.readInt();
+		IModuleResource[] resources2 = new IModuleResource[size];
+		
+		for (int i = 0; i < size; i++) {
+			byte b = in.readByte();
+			if (b == 0) {
+				String name2 = in.readUTF();
+				long stamp = in.readLong();
+				resources2[i] = new ModuleFile(name2, path, stamp);
+			} else if (b == 1) {
+				String name2 = in.readUTF();
+				ModuleFolder folder = new ModuleFolder(null, name2, path);
+				folder.setMembers(loadResource(in, path.append(name2)));
+				resources2[i] = folder;
+			}
+		}
+		
+		return resources2;
+	}
+
+	protected void save(DataOutput out) {
 		try {
-			memento.putString(MODULE_ID, moduleId);
+			out.writeUTF(moduleId);
+			byte b = 0;
 			if (name != null)
-				memento.putString(NAME, name);
+				b &= 1;
+			if (moduleType != null)
+				b &= 2;
+			out.writeByte(b);
+			
+			if (name != null)
+				out.writeUTF(name);
 			
 			if (moduleType != null) {
-				memento.putString(MODULE_TYPE_ID, moduleType.getId());
-				memento.putString(MODULE_TYPE_VERSION, moduleType.getVersion());
+				out.writeUTF(moduleType.getId());
+				out.writeUTF(moduleType.getVersion());
 			}
-			
-			saveResource(memento, resources);
+			saveResource(out, resources);
 		} catch (Exception e) {
 			Trace.trace(Trace.SEVERE, "Could not save module publish info", e);
 		}
 	}
 
-	protected void saveResource(IMemento memento, IModuleResource[] resources2) {
+	protected void saveResource(DataOutput out, IModuleResource[] resources2) throws IOException {
 		if (resources2 == null)
 			return;
 		int size = resources2.length;
+		out.writeInt(0);
 		for (int i = 0; i < size; i++) {
 			if (resources2[i] instanceof IModuleFile) {
 				IModuleFile file = (IModuleFile) resources2[i];
-				IMemento child = memento.createChild(FILE);
-				child.putString(NAME, file.getName());
-				child.putString(STAMP, "" + file.getModificationStamp());
+				out.writeByte(0);
+				out.writeUTF(file.getName());
+				out.writeLong(file.getModificationStamp());
 			} else {
 				IModuleFolder folder = (IModuleFolder) resources2[i];
-				IMemento child = memento.createChild(FOLDER);
-				child.putString(NAME, folder.getName());
+				out.writeByte(1);
+				out.writeUTF(folder.getName());
 				IModuleResource[] resources3 = folder.members();
-				saveResource(child, resources3);
+				saveResource(out, resources3);
 			}
 		}
 	}
diff --git a/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/PublishInfo.java b/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/PublishInfo.java
index 5499e73..17e64bb 100644
--- a/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/PublishInfo.java
+++ b/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/PublishInfo.java
@@ -65,15 +65,16 @@
 		// have we tried loading yet?
 		String serverId = server.getId();
 		if (serverIdToPath.containsKey(serverId)) {
-			if (!serverIdToPublishInfo.containsKey(serverId)) {
-				String partialPath = (String) serverIdToPath.get(serverId);
-				IPath path = ServerPlugin.getInstance().getStateLocation().append(PUBLISH_DIR).append(partialPath);
-				ServerPublishInfo spi = new ServerPublishInfo(path);
-				serverIdToPublishInfo.put(serverId, spi);
-				return spi;
-			}
-			// already loaded
-			return (ServerPublishInfo) serverIdToPublishInfo.get(serverId); 
+			if (serverIdToPublishInfo.containsKey(serverId))
+				return (ServerPublishInfo) serverIdToPublishInfo.get(serverId);
+			
+			// force .dat extension
+			String partialPath = (String) serverIdToPath.get(serverId);
+			partialPath = partialPath.substring(0, partialPath.length() - 3) + "dat";
+			IPath path = ServerPlugin.getInstance().getStateLocation().append(PUBLISH_DIR).append(partialPath);
+			ServerPublishInfo spi = new ServerPublishInfo(path);
+			serverIdToPublishInfo.put(serverId, spi);
+			return spi;
 		}
 		
 		// first time server is being used
@@ -88,7 +89,7 @@
 		ServerPublishInfo spi = null;
 		synchronized (PUBLISH_DIR) {
 			while (file == null || file.exists()) {
-				partialPath = "publish" + i + ".xml";
+				partialPath = "publish" + i + ".dat";
 				path = ServerPlugin.getInstance().getStateLocation().append(PUBLISH_DIR).append(partialPath);
 				if (serverIdToPath.get(partialPath) == null)
 					file = new File(path.toOSString());
diff --git a/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/ServerPublishInfo.java b/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/ServerPublishInfo.java
index 38ef19e..2daf418 100644
--- a/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/ServerPublishInfo.java
+++ b/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/ServerPublishInfo.java
@@ -10,7 +10,13 @@
  **********************************************************************/
 package org.eclipse.wst.server.core.internal;
 
+import java.io.BufferedInputStream;
+import java.io.BufferedOutputStream;
+import java.io.DataInputStream;
+import java.io.DataOutputStream;
 import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
 import java.util.ArrayList;
 import java.util.HashMap;
 import java.util.Iterator;
@@ -251,26 +257,50 @@
 	 */
 	public void load() {
 		String filename = path.toOSString();
-		if (!(new File(filename).exists()))
-			return;
 		
-		Trace.trace(Trace.FINEST, "Loading publish info from " + filename);
-		
-		try {
-			IMemento memento2 = XMLMemento.loadMemento(filename);
-			Float f = memento2.getFloat(VERSION);
-			if (f != null && f.floatValue() >= 3)
-				return;
+		if (new File(filename).exists()) {
+			Trace.trace(Trace.FINEST, "Loading publish info from " + filename);
 			
-			IMemento[] children = memento2.getChildren("module");
-			
-			int size = children.length;
-			for (int i = 0; i < size; i++) {
-				ModulePublishInfo mpi = new ModulePublishInfo(children[i]);
-				modulePublishInfo.put(getKey(mpi.getModuleId()), mpi);
+			DataInputStream in = null;
+			try {
+				in = new DataInputStream(new BufferedInputStream(new FileInputStream(filename)));
+				in.readByte();
+				in.readByte();
+				// version
+				int ver = in.readByte();
+				if (ver <= 1) {
+					int size = in.readInt();	
+					for (int i = 0; i < size; i++) {
+						ModulePublishInfo mpi = new ModulePublishInfo(in);
+						modulePublishInfo.put(getKey(mpi.getModuleId()), mpi);
+					}
+					return;
+				}
+			} catch (Exception e) {
+				Trace.trace(Trace.WARNING, "Could not load publish information: " + e.getMessage());
 			}
-		} catch (Exception e) {
-			Trace.trace(Trace.WARNING, "Could not load publish information: " + e.getMessage());
+		}
+		
+		filename = filename.substring(0, filename.length() - 3) + "xml";
+		if (new File(filename).exists()) {
+			Trace.trace(Trace.FINEST, "Loading publish info from old format " + filename);
+			
+			try {
+				IMemento memento2 = XMLMemento.loadMemento(filename);
+				Float f = memento2.getFloat(VERSION);
+				if (f != null && f.floatValue() >= 3)
+					return;
+				
+				IMemento[] children = memento2.getChildren("module");
+				
+				int size = children.length;
+				for (int i = 0; i < size; i++) {
+					ModulePublishInfo mpi = new ModulePublishInfo(children[i]);
+					modulePublishInfo.put(getKey(mpi.getModuleId()), mpi);
+				}
+			} catch (Exception e) {
+				Trace.trace(Trace.WARNING, "Could not load publish information: " + e.getMessage());
+			}
 		}
 	}
 
@@ -281,21 +311,36 @@
 		String filename = path.toOSString();
 		Trace.trace(Trace.FINEST, "Saving publish info to " + filename);
 		
+		DataOutputStream out = null;
 		try {
-			XMLMemento memento = XMLMemento.createWriteRoot("server");
-			memento.putString(VERSION, "2.0");
+			out = new DataOutputStream(new BufferedOutputStream(new FileOutputStream(filename)));
+			out.writeByte(14);
+			out.writeByte(14);
+			// version
+			out.writeByte(1);
 			
+			out.writeInt(modulePublishInfo.keySet().size());
 			Iterator iterator = modulePublishInfo.keySet().iterator();
 			while (iterator.hasNext()) {
 				String controlRef = (String) iterator.next();
 				ModulePublishInfo mpi = (ModulePublishInfo) modulePublishInfo.get(controlRef);
-				IMemento child = memento.createChild("module");
-				mpi.save(child);
+				mpi.save(out);
 			}
-			memento.saveToFile(filename);
 		} catch (Exception e) {
 			Trace.trace(Trace.SEVERE, "Could not save publish information", e);
+		} finally {
+			try {
+				out.close();
+			} catch (Exception e) {
+				// ignore
+			}
 		}
+		
+		// remove old file
+		filename = filename.substring(0, filename.length() - 3) + "xml";
+		File f = new File(filename);
+		if (f.exists())
+			f.delete();
 	}
 
 	/**
diff --git a/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/XMLMemento.java b/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/XMLMemento.java
index 0f91a1a..8c0dac2 100644
--- a/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/XMLMemento.java
+++ b/plugins/org.eclipse.wst.server.core/servercore/org/eclipse/wst/server/core/internal/XMLMemento.java
@@ -365,9 +365,9 @@
 	 * @exception java.io.IOException
 	 */
 	public void saveToFile(String filename) throws IOException {
-		FileOutputStream w = null;
+		BufferedOutputStream w = null;
 		try {
-			w = new FileOutputStream(filename);
+			w = new BufferedOutputStream(new FileOutputStream(filename));
 			save(w);
 		} catch (IOException e) {
 			throw e;