*** empty log message ***
diff --git a/bundles/org.eclipse.core.runtime/plugin.xml b/bundles/org.eclipse.core.runtime/plugin.xml
index eeb27a1..c98bfa8 100644
--- a/bundles/org.eclipse.core.runtime/plugin.xml
+++ b/bundles/org.eclipse.core.runtime/plugin.xml
@@ -2,7 +2,7 @@
 <plugin
   name="%pluginName"
   id="org.eclipse.core.runtime"
-  version="2.0.13"
+  version="2.0.14"
   provider-name="%providerName">
 
   <runtime>
diff --git a/bundles/org.eclipse.core.runtime/src/org/eclipse/core/internal/runtime/Cipher.java b/bundles/org.eclipse.core.runtime/src/org/eclipse/core/internal/runtime/Cipher.java
index 6f10648..907e860 100644
--- a/bundles/org.eclipse.core.runtime/src/org/eclipse/core/internal/runtime/Cipher.java
+++ b/bundles/org.eclipse.core.runtime/src/org/eclipse/core/internal/runtime/Cipher.java
@@ -20,11 +20,11 @@
  *
  *     // Encrypt
  *     Cipher cipher = new Cipher(ENCRYPT_MODE, password);
- *     byte[] encrypted = cipher.update(data);
+ *     byte[] encrypted = cipher.cipher(data);
  *
  *     // Decrypt
  *     cipher = new Cipher(DECRYPT_MODE, password);
- *     byte[] decrypted = cipher.update(encrypted);
+ *     byte[] decrypted = cipher.cipher(encrypted);
  * </pre>
  */
 public class Cipher {
diff --git a/bundles/org.eclipse.core.runtime/src/org/eclipse/core/internal/runtime/PlatformLogReader.java b/bundles/org.eclipse.core.runtime/src/org/eclipse/core/internal/runtime/PlatformLogReader.java
index 6cc558b..3535e5c 100644
--- a/bundles/org.eclipse.core.runtime/src/org/eclipse/core/internal/runtime/PlatformLogReader.java
+++ b/bundles/org.eclipse.core.runtime/src/org/eclipse/core/internal/runtime/PlatformLogReader.java
@@ -1,69 +1,47 @@
+/*******************************************************************************
+ * Copyright (c) 2000,2002 IBM Corporation and others.
+ * All rights reserved.   This program and the accompanying materials
+ * are made available under the terms of the Common Public License v0.5
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/cpl-v05.html
+ * 
+ * Contributors:
+ * IBM - Initial API and implementation
+ ******************************************************************************/
 package org.eclipse.core.internal.runtime;
 
 import java.io.*;
-import java.util.*;
-
-import org.apache.xerces.parsers.SAXParser;
-import org.eclipse.core.internal.boot.DelegatingURLClassLoader;
-import org.eclipse.core.internal.boot.PlatformClassLoader;
+import java.util.ArrayList;
+import java.util.StringTokenizer;
+import org.eclipse.core.internal.runtime.*;
 import org.eclipse.core.runtime.*;
-import org.xml.sax.*;
-import org.xml.sax.helpers.AttributesImpl;
-import org.xml.sax.helpers.DefaultHandler;
 
 /**
  * Reads a structured log from disk and reconstructs status and exception objects.
  * General strategy: log entries that are malformed in any way are skipped, and an extra
  * status is returned mentioned that there were problems.
  */
-public class PlatformLogReader extends DefaultHandler {
-	private static final String NULL_STRING = "" + null;
-	private ArrayList result = null;
-	private Stack objectStack = null;
+public class PlatformLogReader {
+	private ArrayList list = null;
+	private String currentLine = "";
+	private BufferedReader reader;
 
-/**
- * Returns a severity given its string representation.  
- * Converse of PlatformLogReader#encodeSeverity.
- */
-protected int decodeSeverity(String severity) {
-	if (severity == null)
-		return -1;
-	if (severity.equals("ERROR"))
-		return IStatus.ERROR;
-	if (severity.equals("INFO"))
-		return IStatus.INFO;
-	if (severity.equals("WARNING"))
-		return IStatus.WARNING;
-	if (severity.equals("OK"))
-		return IStatus.OK;
-	try {
-		return Integer.parseInt(severity);
-	} catch (NumberFormatException e) {
-		return -1;
-	}
-}
-public void endElement(String uri, String elementName, String qName) {
-	if (elementName.equals(PlatformLogWriter.ELEMENT_LOG_ENTRY)) {
-		readLogEntry();
-	} else if (elementName.equals(PlatformLogWriter.ELEMENT_STATUS)) {
-		readStatus();
-	} else if (elementName.equals(PlatformLogWriter.ELEMENT_EXCEPTION)) {
-		readException();
-	}
-}
-/**
- * @see org.xml.sax.ErrorHandler#error.
- */
-public void error(SAXParseException ex) {
-	log(ex);
-}
-/**
- * @see org.xml.sax.ErrorHandler#fatalError
- */
-public void fatalError(SAXParseException ex) throws SAXException {
-	log(ex);
-	throw ex;
-}
+	// constants copied from the PlatformLogWriter (since they are private
+	// to that class and this class should be used only in test suites)
+	private static final String KEYWORD_SESSION = "!SESSION";
+	private static final String KEYWORD_ENTRY = "!ENTRY";
+	private static final String KEYWORD_SUBENTRY = "!SUBENTRY";
+	private static final String KEYWORD_MESSAGE = "!MESSAGE";
+	private static final String KEYWORD_STACK = "!STACK";
+
+	private static final int NULL = -2;
+	private static final int SESSION = 1;
+	private static final int ENTRY = 2;
+	private static final int SUBENTRY = 4;
+	private static final int MESSAGE = 8;
+	private static final int STACK = 16;
+	private static final int UNKNOWN = 32;
+
 /**
  * Given a stack trace without carriage returns, returns a pretty-printed stack.
  */
@@ -91,101 +69,78 @@
 	writer.close();
 	return sWriter.toString();
 }
-protected String getString(Attributes attributes, String attributeName) {
-	return attributes.getValue(attributeName);
-}
 protected void log(Exception ex) {
 	String msg = Policy.bind("meta.exceptionParsingLog", ex.getMessage());
-	result.add(new Status(IStatus.WARNING, Platform.PI_RUNTIME, Platform.PARSE_PROBLEM, msg, ex));
+	list.add(new Status(IStatus.WARNING, Platform.PI_RUNTIME, Platform.PARSE_PROBLEM, msg, ex));
 }
-protected void readException() {
-	Attributes attributes = (Attributes)objectStack.pop();
-	String message = getString(attributes, PlatformLogWriter.ATTRIBUTE_MESSAGE);
-	if (NULL_STRING.equals(message)) {
-		message = null;
-	}
-	String stack = getString(attributes, PlatformLogWriter.ATTRIBUTE_TRACE);
-	objectStack.push(new FakeException(message, formatStack(stack)));
-}
-protected void readLogEntry() {
-	while (!objectStack.isEmpty()) {
-		Object o = objectStack.pop();
-		if (o instanceof IStatus) {
-			result.add(o);
-		}
-	}
+protected Throwable readException(String message) throws IOException {
+	if (currentLine == null || getLineType() != STACK)
+		return null;
+	StringBuffer buffer = new StringBuffer();
+	buffer.append(currentLine.substring(KEYWORD_STACK.length()+1, currentLine.length()));
+	currentLine = reader.readLine();
+	buffer.append(readText());
+	String stack = buffer.toString();
+	return new FakeException(null, formatStack(stack));
 }
 /**
  * Reads the given log file and returns the contained status objects. 
  * If the log file could not be read, a status object indicating this fact
  * is returned.
  */
-public IStatus[] readLogFile(String path) {
-	result = new ArrayList();
-	objectStack = new Stack();
-	//XXX workaround.  See Bug 5801.
-	DelegatingURLClassLoader xmlClassLoader = (DelegatingURLClassLoader)Platform.getPluginRegistry().getPluginDescriptor("org.apache.xerces").getPluginClassLoader();
-	PlatformClassLoader.getDefault().setImports(new DelegatingURLClassLoader[] { xmlClassLoader });
+public synchronized IStatus[] readLogFile(String path) {
+	list = new ArrayList();
+	InputStream input = null;
 	try {
-		Reader reader = new BufferedReader(new FileReader(path));
-		SAXParser parser = new SAXParser();
-		parser.setContentHandler(this);
-		parser.setErrorHandler(this);
-		parser.parse(new InputSource(reader));
-	} catch (IllegalStateException e) {
-		log(e);
+		input = new FileInputStream(path);
+		reader = new BufferedReader(new InputStreamReader(input, "UTF-8"));//$NON-NLS-1$
+		currentLine = reader.readLine();
+		while (currentLine != null) {
+			switch (getLineType()) {
+				case ENTRY:
+					IStatus status = readEntry();
+					if (status != null)
+						list.add(status);
+					break;
+				case SUBENTRY:
+				case MESSAGE:
+				case STACK:
+				case SESSION:
+				case UNKNOWN:
+					currentLine = reader.readLine();
+					break;
+			}
+		}
 	} catch (IOException e) {
 		log(e);
-	}catch (SAXException e) {
-		log(e);
-	}finally {
-		PlatformClassLoader.getDefault().setImports(null);
-	}
-	return (IStatus[]) result.toArray(new IStatus[result.size()]);
-}
-protected void readStatus() {
-	//status children are either child statii or an exception
-	Attributes attributes = null;
-	Throwable exception = null;
-	ArrayList children = new ArrayList();
-	while (!objectStack.isEmpty()) {
-		Object o = objectStack.pop();
-		if (o instanceof IStatus) {
-			//stacking reversed order, so reverse order on pop
-			children.add(0, o);
-		} else if (o instanceof Throwable) {
-			exception = (Throwable)o;
-		} else {
-			attributes = (Attributes)o;
-			break;
+	} finally {
+		try {
+			if (input != null)
+				input.close();
+		} catch (IOException e) {
+			log(e);
 		}
 	}
-	if (attributes == null) 
-		throw new IllegalStateException("Status missing attributes");//$NON-NLS$
-	int severity = decodeSeverity(getString(attributes, PlatformLogWriter.ATTRIBUTE_SEVERITY));
-	String pluginID = getString(attributes, PlatformLogWriter.ATTRIBUTE_PLUGIN_ID);
-	String s = getString(attributes, PlatformLogWriter.ATTRIBUTE_CODE);
-	int code = s == null ? -1 : Integer.parseInt(s);
-	String message = getString(attributes, PlatformLogWriter.ATTRIBUTE_MESSAGE);
-	if (severity == -1 || pluginID == null || code == -1 || message == null)
-		throw new IllegalStateException();
+	return (IStatus[]) list.toArray(new IStatus[list.size()]);
+}
+protected int getLineType() {
+	if (currentLine == null) 
+		return NULL;
+	StringTokenizer tokenizer = new StringTokenizer(currentLine);
+	String token = tokenizer.nextToken();
+	if (token.equals(KEYWORD_SESSION))
+		return SESSION;
+	if (token.equals(KEYWORD_ENTRY))
+		return ENTRY;
+	if (token.equals(KEYWORD_SUBENTRY))
+		return SUBENTRY;
+	if (token.equals(KEYWORD_MESSAGE))
+		return MESSAGE;
+	if (token.equals(KEYWORD_STACK))
+		return STACK;
+	return UNKNOWN;
+}
 
-	if (children.size() > 0) {
-		IStatus[] childStatii = (IStatus[]) children.toArray(new IStatus[children.size()]);
-		objectStack.push(new MultiStatus(pluginID, code, childStatii, message, exception));
-	} else {
-		objectStack.push(new Status(severity, pluginID, code, message, exception));
-	}
-}
-public void startElement(String uri, String elementName, String qName, Attributes attributes) {
-	objectStack.push(new AttributesImpl(attributes));
-}
-/**
- * @see org.xml.sax.ErrorHandler#warning.
- */
-public void warning(SAXParseException ex) {
-	log(ex);
-}	
 /**
  * A reconsituted exception that only contains a stack trace and a message.
  */
@@ -209,5 +164,94 @@
 		stream.println(stackTrace);
 	}		
 }
+protected IStatus readEntry() throws IOException {
+	if (currentLine == null || getLineType() != ENTRY)
+		return null;
+	StringTokenizer tokens = new StringTokenizer(currentLine);
+	// skip over the ENTRY keyword
+	tokens.nextToken();
+	String pluginID = tokens.nextToken();
+	int severity = Integer.parseInt(tokens.nextToken());
+	int code = Integer.parseInt(tokens.nextToken());
+	// ignore the rest of the line since its the date
+	currentLine = reader.readLine();
+	String message = readMessage();
+	Throwable exception = readException(message);
+	if (currentLine == null || getLineType() != SUBENTRY)
+		return new Status(severity, pluginID, code, message, exception);
+	MultiStatus parent = new MultiStatus(pluginID, code, message, exception);
+	readSubEntries(parent);
+	return parent;
 }
+protected void readSubEntries(MultiStatus parent) throws IOException {
+	while (getLineType() == SUBENTRY) {
+		StringTokenizer tokens = new StringTokenizer(currentLine);
+		// skip over the subentry keyword
+		tokens.nextToken();
+		int currentDepth = Integer.parseInt(tokens.nextToken());
+		String pluginID = tokens.nextToken();
+		int severity = Integer.parseInt(tokens.nextToken());
+		int code = Integer.parseInt(tokens.nextToken());
+		// ignore the rest of the line since its the date
+		currentLine = reader.readLine();
+		String message = readMessage();
+		Throwable exception = readException(message);
+	
+		IStatus current = new Status(severity, pluginID, code, message, exception);
+		if (currentLine == null || getLineType() != SUBENTRY) {
+			parent.add(current);
+			return;
+		}
 
+		tokens = new StringTokenizer(currentLine);
+		tokens.nextToken();
+		int depth = Integer.parseInt(tokens.nextToken());
+		if (currentDepth == depth) {
+			// next sub-entry is a sibling
+			parent.add(current);
+		} else if (currentDepth == (depth - 1)) {
+			// next sub-entry is a child
+			current = new MultiStatus(pluginID, code, message, exception);
+			readSubEntries((MultiStatus) current);
+			parent.add(current);
+		} else {
+			parent.add(current);
+			return;
+		}
+	}
+}
+protected int readDepth() throws IOException {
+	StringTokenizer tokens = new StringTokenizer(currentLine);
+	// skip the keyword
+	tokens.nextToken();
+	return Integer.parseInt(tokens.nextToken());
+}
+protected String readMessage() throws IOException {
+	if (currentLine == null || getLineType() != MESSAGE)
+		return "";
+	StringBuffer buffer = new StringBuffer();
+	buffer.append(currentLine.substring(KEYWORD_MESSAGE.length()+1, currentLine.length()));
+	currentLine = reader.readLine();
+	buffer.append(readText());
+	return buffer.toString();
+}
+protected String readText() throws IOException {
+	StringBuffer buffer = new StringBuffer();
+	if (currentLine == null || getLineType() != UNKNOWN)
+		return "";
+	else buffer.append(currentLine);
+	boolean done = false;
+	while (!done) {
+		currentLine = reader.readLine();
+		if (currentLine == null) {
+			done = true;
+			continue;
+		}
+		if (getLineType() == UNKNOWN)
+			buffer.append(currentLine);
+		else
+			done = true;
+	}
+	return buffer.toString();
+}
+}
diff --git a/bundles/org.eclipse.core.runtime/src/org/eclipse/core/internal/runtime/PlatformLogWriter.java b/bundles/org.eclipse.core.runtime/src/org/eclipse/core/internal/runtime/PlatformLogWriter.java
index 26e5e1e..11796b3 100644
--- a/bundles/org.eclipse.core.runtime/src/org/eclipse/core/internal/runtime/PlatformLogWriter.java
+++ b/bundles/org.eclipse.core.runtime/src/org/eclipse/core/internal/runtime/PlatformLogWriter.java
@@ -1,11 +1,17 @@
+/*******************************************************************************
+ * Copyright (c) 2000,2002 IBM Corporation and others.
+ * All rights reserved.   This program and the accompanying materials
+ * are made available under the terms of the Common Public License v0.5
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/cpl-v05.html
+ * 
+ * Contributors:
+ * IBM - Initial API and implementation
+ ******************************************************************************/
 package org.eclipse.core.internal.runtime;
 
-/*
- * (c) Copyright IBM Corp. 2000, 2001.
- * All Rights Reserved.
- */
-
 import java.io.*;
+import java.text.DateFormat;
 import java.util.*;
 
 import org.eclipse.core.runtime.ILogListener;
@@ -17,112 +23,42 @@
 public class PlatformLogWriter implements ILogListener {
 	protected File logFile = null;
 	protected Writer log = null;
-	protected int tabDepth;
-	
-	protected static final String LINE_SEPARATOR;
-	protected static final String TAB_STRING = "  ";
-	
-	protected static final String XML_VERSION = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>";
+	protected boolean newSession = true;
 
-	protected static final String ATTRIBUTE_DATE = "date";
-	protected static final String ATTRIBUTE_SEVERITY = "severity";
-	protected static final String ATTRIBUTE_PLUGIN_ID = "plugin-id";
-	protected static final String ATTRIBUTE_CODE = "code";
-	protected static final String ATTRIBUTE_MESSAGE = "message";
-	protected static final String ATTRIBUTE_TRACE = "trace";
-	
-	protected static final String ELEMENT_LOG = "log";
-	protected static final String ELEMENT_LOG_ENTRY = "log-entry";
-	protected static final String ELEMENT_STATUS = "status";
-	protected static final String ELEMENT_EXCEPTION = "exception";
+	protected static final String SESSION = "!SESSION";//$NON-NLS-1$
+	protected static final String ENTRY = "!ENTRY";//$NON-NLS-1$
+	protected static final String SUBENTRY = "!SUBENTRY";//$NON-NLS-1$
+	protected static final String MESSAGE = "!MESSAGE";//$NON-NLS-1$
+	protected static final String STACK = "!STACK";//$NON-NLS-1$
+
+	protected static final String LINE_SEPARATOR;
+	protected static final String TAB_STRING = "\t";//$NON-NLS-1$
 
 	static {
-		String s = System.getProperty("line.separator");
-		LINE_SEPARATOR = s == null ? "\n" : s;
+		String s = System.getProperty("line.separator");//$NON-NLS-1$
+		LINE_SEPARATOR = s == null ? "\n" : s;//$NON-NLS-1$
 	}
 
 public PlatformLogWriter(File file) {
 	this.logFile = file;
-	// remove old log file
-	logFile.delete();
 }
 /**
  * This constructor should only be used to pass System.out .
  */
 public PlatformLogWriter(OutputStream out) {
-	log = new OutputStreamWriter(out);
-}
-protected static void appendEscapedChar(StringBuffer buffer, char c) {
-	String replacement = getReplacement(c);
-	if (replacement != null) {
-		buffer.append('&');
-		buffer.append(replacement);
-		buffer.append(';');
-	} else {
-		buffer.append(c);
-	}
-}
-protected static String getEscaped(String s) {
-	StringBuffer result = new StringBuffer(s.length() + 10);
-	for (int i = 0; i < s.length(); ++i)
-		appendEscapedChar(result, s.charAt(i));
-	return result.toString();
-}
-protected static String getReplacement(char c) {
-	// Encode special XML characters into the equivalent character references.
-	// These five are defined by default for all XML documents.
-	switch (c) {
-		case '<' :
-			return "lt";
-		case '>' :
-			return "gt";
-		case '"' :
-			return "quot";
-		case '\'' :
-			return "apos";
-		case '&' :
-			return "amp";
-	}
-	return null;
+	this.log = logForStream(out);
 }
 protected void closeLogFile() throws IOException {
 	try {
-		log.flush();
-		log.close();
+		if (log != null) {
+			log.flush();
+			log.close();
+		}
 	} finally {
 		log = null;
 	}
 }
 /**
- * Returns a string representation of the given severity.
- */
-protected String encodeSeverity(int severity) {
-	switch (severity) {
-		case IStatus.ERROR :
-			return "ERROR";
-		case IStatus.INFO :
-			return "INFO";
-		case IStatus.OK:
-			return "OK";
-		case IStatus.WARNING :
-			return "WARNING";
-	}
-	//unknown severity, just print the integer
-	return Integer.toString(severity);
-}
-protected String encodeStackTrace(Throwable t) {
-	StringWriter sWriter = new StringWriter();
-	PrintWriter pWriter = new PrintWriter(sWriter);
-	pWriter.println();
-	t.printStackTrace(pWriter);
-	pWriter.flush();
-	return sWriter.toString();
-}
-protected void endTag(String name) throws IOException {
-	tabDepth--;
-	printTag('/' + name, null);
-}
-/**
  * @see ILogListener#logging.
  */
 public synchronized void logging(IStatus status, String plugin) {
@@ -130,10 +66,10 @@
 	if (logFile != null)
 		openLogFile();
 	if (log == null)
-		log = new OutputStreamWriter(System.err);
+		log = logForStream(System.err);
 	try {
 		try {
-			writeLogEntry(status);
+			write(status, 0);
 		} finally {
 			if (logFile != null)
 				closeLogFile();
@@ -141,16 +77,16 @@
 				log.flush();
 		}			
 	} catch (Exception e) {
-		System.err.println("An exception occurred while writing to the platform log:");
+		System.err.println("An exception occurred while writing to the platform log:");//$NON-NLS-1$
 		System.err.println(e.getClass().getName() + ": " + e.getMessage());
-		System.err.println("Logging to the console instead.");
+		System.err.println("Logging to the console instead.");//$NON-NLS-1$
 		//we failed to write, so dump log entry to console instead
 		try {
-			log = new OutputStreamWriter(System.err);
-			writeLogEntry(status);
+			log = logForStream(System.err);
+			write(status, 0);
 			log.flush();
 		} catch (Exception e2) {
-			System.err.println("An exception occurred while logging to the console:");
+			System.err.println("An exception occurred while logging to the console:");//$NON-NLS-1$
 			System.err.println(e.getClass().getName() + ": " + e.getMessage());
 		}
 	} finally {
@@ -159,50 +95,29 @@
 }
 protected void openLogFile() {
 	try {
-		boolean newLog = !logFile.exists();
-		log =new BufferedWriter(new FileWriter(logFile.getAbsolutePath(), true));
-		if (newLog) {
-			println(XML_VERSION);
-			startTag(ELEMENT_LOG, null);
+		log = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(logFile.getAbsolutePath(), true), "UTF-8"));
+		if (newSession) {
+			writeln(SESSION);
+			newSession = false;
 		}
 	} catch (IOException e) {
 		// there was a problem opening the log file so log to the console
-		log = new OutputStreamWriter(System.err);
+		log = logForStream(System.err);
+	}
+}
+protected Writer logForStream(OutputStream output) {
+	try {
+		return new BufferedWriter(new OutputStreamWriter(output, "UTF-8"));//$NON-NLS-1$
+	} catch (UnsupportedEncodingException e) {
+		return new BufferedWriter(new OutputStreamWriter(output));
 	}
 }
 /**
  * Writes the given string to the log, followed by the line terminator string.
  */
-protected void println(String s) throws IOException {
-	log.write(s);
-	log.write(LINE_SEPARATOR);
-}
-protected void printTabulation() throws IOException {
-	for (int i = 0; i < tabDepth; i++)
-		log.write(TAB_STRING);
-}
-
-protected void printTag(String name, HashMap parameters) throws IOException {
-	printTabulation();
-	log.write('<');
-	log.write(name);
-	tabDepth++;
-	if (parameters != null)
-		for (Enumeration enum = Collections.enumeration(parameters.keySet()); enum.hasMoreElements();) {
-			//new line for each attribute if there's more than one
-			if (parameters.size() > 1) {
-				log.write(LINE_SEPARATOR);
-				printTabulation();
-			}
-			log.write(" ");
-			String key = (String) enum.nextElement();
-			log.write(key);
-			log.write("=\"");
-			log.write(getEscaped(String.valueOf(parameters.get(key))));
-			log.write("\"");
-		}
-	tabDepth--;
-	println(">");
+protected void writeln(String s) throws IOException {
+	write(s);
+	writeln();
 }
 /**
  * Shuts down the platform log.
@@ -210,13 +125,8 @@
 public synchronized void shutdown() {
 	try {
 		if (logFile != null) {
-			try {
-				openLogFile();
-				endTag(ELEMENT_LOG);
-			} finally {
-				closeLogFile();
-				logFile = null;
-			}
+			closeLogFile();
+			logFile = null;
 		} else {
 			if (log != null) {
 				Writer old = log;
@@ -230,43 +140,59 @@
 		e.printStackTrace();
 	}
 }
-protected void startTag(String name, HashMap parameters) throws IOException {
-	printTag(name, parameters);
-	tabDepth++;
-}
+
 protected void write(Throwable throwable) throws IOException {
 	if (throwable == null)
 		return;
-	HashMap attributes = new HashMap();
-	attributes.put(ATTRIBUTE_MESSAGE, throwable.getMessage());
-	attributes.put(ATTRIBUTE_TRACE, encodeStackTrace(throwable));
-	startTag(ELEMENT_EXCEPTION, attributes);
-	endTag(ELEMENT_EXCEPTION);
+	write(STACK);
+	writeSpace();
+	StringBuffer buffer = new StringBuffer();
+	throwable.printStackTrace(new PrintWriter(log));
 }
-protected void write(IStatus status) throws IOException {
-	HashMap attributes = new HashMap();
-	attributes.put(ATTRIBUTE_SEVERITY, encodeSeverity(status.getSeverity()));
-	attributes.put(ATTRIBUTE_PLUGIN_ID, status.getPlugin());
-	attributes.put(ATTRIBUTE_CODE, Integer.toString(status.getCode()));
-	attributes.put(ATTRIBUTE_MESSAGE, status.getMessage());
-	startTag(ELEMENT_STATUS, attributes); {
-		write(status.getException());
-		if (status.isMultiStatus()) {
-			IStatus[] children = status.getChildren();
-			for (int i = 0; i < children.length; i++) {
-				write(children[i]);
-			}
+
+
+protected void write(IStatus status, int depth) throws IOException {
+	if (depth == 0)
+		write(ENTRY);
+	else
+		write(SUBENTRY);
+	if (depth != 0) {
+		writeSpace();
+		write(Integer.toString(depth));
+	}
+	writeSpace();
+	write(status.getPlugin());
+	writeSpace();
+	write(Integer.toString(status.getSeverity()));
+	writeSpace();
+	write(Integer.toString(status.getCode()));
+	writeSpace();
+	write(new Date().toString());
+	writeln();
+
+	write(MESSAGE);
+	writeSpace();
+	writeln(status.getMessage());
+
+	write(status.getException());
+
+	if (status.isMultiStatus()) {
+		IStatus[] children = status.getChildren();
+		for (int i = 0; i < children.length; i++) {
+			write(children[i], depth+1);
 		}
 	}
-	endTag(ELEMENT_STATUS);
 }
-protected void writeLogEntry(IStatus status) throws IOException {
-	tabDepth = 0;
-	HashMap attributes = new HashMap();
-	attributes.put(ATTRIBUTE_DATE, new Date());
-	startTag(ELEMENT_LOG_ENTRY, attributes);
-	write(status);
-	endTag(ELEMENT_LOG_ENTRY);
+
+protected void writeln() throws IOException {
+	write(LINE_SEPARATOR);
 }
+protected void write(String message) throws IOException {
+	log.write(message);
+}
+protected void writeSpace() throws IOException {
+	write(" ");//$NON-NLS-1$
+}
+
 }