Use local copy of latest bndlib code for pre-release testing purposes

git-svn-id: https://svn.apache.org/repos/asf/felix/trunk@1347815 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/bundleplugin/src/main/java/aQute/lib/json/MapHandler.java b/bundleplugin/src/main/java/aQute/lib/json/MapHandler.java
new file mode 100644
index 0000000..5a413b6
--- /dev/null
+++ b/bundleplugin/src/main/java/aQute/lib/json/MapHandler.java
@@ -0,0 +1,91 @@
+package aQute.lib.json;
+
+import java.io.*;
+import java.lang.reflect.*;
+import java.util.*;
+
+public class MapHandler extends Handler {
+	final Class<?>	rawClass;
+	final Type		keyType;
+	final Type		valueType;
+
+	MapHandler(Class<?> rawClass, Type keyType, Type valueType) {
+		this.keyType = keyType;
+		this.valueType = valueType;
+		if (rawClass.isInterface()) {
+			if (rawClass.isAssignableFrom(HashMap.class))
+				rawClass = HashMap.class;
+			else if (rawClass.isAssignableFrom(TreeMap.class))
+				rawClass = TreeMap.class;
+			else if (rawClass.isAssignableFrom(Hashtable.class))
+				rawClass = Hashtable.class;
+			else if (rawClass.isAssignableFrom(LinkedHashMap.class))
+				rawClass = LinkedHashMap.class;
+			else
+				throw new IllegalArgumentException("Unknown map interface: " + rawClass);
+		}
+		this.rawClass = rawClass;
+	}
+
+	@Override void encode(Encoder app, Object object, Map<Object, Type> visited)
+			throws IOException, Exception {
+		Map<?, ?> map = (Map<?, ?>) object;
+
+		app.append("{");
+		String del = "";
+		for (Map.Entry<?, ?> e : map.entrySet()) {
+			app.append(del);
+			String key;
+			if (e.getKey() != null && (keyType == String.class || keyType == Object.class))
+				key = e.getKey().toString();
+			else {
+				key = app.codec.enc().put(e.getKey()).toString();
+			}
+			StringHandler.string(app, key);
+			app.append(":");
+			app.encode(e.getValue(), valueType, visited);
+			del = ",";
+		}
+		app.append("}");
+	}
+
+	@SuppressWarnings("unchecked") @Override Object decodeObject(Decoder r) throws Exception {
+		assert r.current() == '{';
+		
+		Map<Object, Object> map = (Map<Object, Object>) rawClass.newInstance();
+		
+		int c = r.next();
+		while (JSONCodec.START_CHARACTERS.indexOf(c) >= 0) {
+			Object key = r.codec.parseString(r);
+			if ( !(keyType == null || keyType == Object.class)) {
+				Handler h = r.codec.getHandler(keyType);
+				key = h.decode((String)key);
+			}
+			
+			c = r.skipWs();
+			if ( c != ':')
+				throw new IllegalArgumentException("Expected ':' but got " + (char) c);
+
+			c = r.next();
+			Object value = r.codec.decode(valueType, r);
+			map.put(key, value);
+
+			c = r.skipWs();
+			
+			if (c == '}') 
+				break;
+
+			if (c == ',') {
+				c = r.next();
+				continue;
+			}
+
+			throw new IllegalArgumentException(
+					"Invalid character in parsing list, expected } or , but found " + (char) c);
+		}
+		assert r.current() == '}';
+		r.read(); // skip closing
+		return map;
+	}
+
+}