summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorRich Hickey <richhickey@gmail.com>2009-03-03 22:31:55 +0000
committerRich Hickey <richhickey@gmail.com>2009-03-03 22:31:55 +0000
commit69728918d3e00f821903e7e12771d4332937e288 (patch)
tree1d953d1e2f8c1de911d612e751d66d5521789395 /src
parent9723a7b5d693bec38dc57269b423094ababa9dd1 (diff)
restore list constants as PersistentLists
Diffstat (limited to 'src')
-rw-r--r--src/jvm/clojure/lang/Compiler.java211
1 files changed, 127 insertions, 84 deletions
diff --git a/src/jvm/clojure/lang/Compiler.java b/src/jvm/clojure/lang/Compiler.java
index 0b2b316c..e683da91 100644
--- a/src/jvm/clojure/lang/Compiler.java
+++ b/src/jvm/clojure/lang/Compiler.java
@@ -3188,90 +3188,133 @@ static public class FnExpr implements Expr{
// getCompiledClass();
}
- void emitListAsObjectArray(Object value, GeneratorAdapter gen) {
- gen.push(((List)value).size());
- gen.newArray(OBJECT_TYPE);
- int i = 0;
- for (Iterator it = ((List)value).iterator(); it.hasNext(); i++) {
- gen.dup();
- gen.push(i);
- emitValue(it.next(), gen);
- gen.arrayStore(OBJECT_TYPE);
- }
- }
-
- void emitValue(Object value, GeneratorAdapter gen) {
- boolean partial = true;
- //System.out.println(value.getClass().toString());
-
- if (value instanceof String) {
- gen.push((String)value);
- } else if (value instanceof Integer) {
- gen.push(((Integer)value).intValue());
- gen.invokeStatic(Type.getType(Integer.class), Method.getMethod("Integer valueOf(int)"));
- } else if (value instanceof Double) {
- gen.push(((Double)value).doubleValue());
- gen.invokeStatic(Type.getType(Double.class), Method.getMethod("Double valueOf(double)"));
- } else if (value instanceof Character) {
- gen.push(((Character)value).charValue());
- gen.invokeStatic(Type.getType(Character.class), Method.getMethod("Character valueOf(char)"));
- } else if (value instanceof Class) {
- gen.push(((Class)value).getName());
- gen.invokeStatic(Type.getType(Class.class), Method.getMethod("Class forName(String)"));
- } else if (value instanceof Symbol) {
- gen.push(((Symbol)value).ns);
- gen.push(((Symbol)value).name);
- gen.invokeStatic(Type.getType(Symbol.class), Method.getMethod("clojure.lang.Symbol create(String,String)"));
- } else if (value instanceof Keyword) {
- emitValue(((Keyword)value).sym,gen);
- gen.invokeStatic(Type.getType(Keyword.class), Method.getMethod("clojure.lang.Keyword intern(clojure.lang.Symbol)"));
- } else if (value instanceof Var) {
- Var var = (Var) value;
- gen.push(var.ns.name.toString());
- gen.push(var.sym.toString());
- gen.invokeStatic(RT_TYPE, Method.getMethod("clojure.lang.Var var(String,String)"));
- } else if (value instanceof IPersistentMap) {
- List entries = new ArrayList();
- for (Map.Entry entry : (Set<Map.Entry>) ((Map)value).entrySet()) {
- entries.add(entry.getKey());
- entries.add(entry.getValue());
- }
- emitListAsObjectArray(entries, gen);
- gen.invokeStatic(RT_TYPE, Method.getMethod("clojure.lang.IPersistentMap map(Object[])"));
- } else if (value instanceof IPersistentVector) {
- emitListAsObjectArray(value, gen);
- gen.invokeStatic(RT_TYPE, Method.getMethod("clojure.lang.IPersistentVector vector(Object[])"));
- } else if (value instanceof ISeq || value instanceof IPersistentList) {
- emitListAsObjectArray(value, gen);
- gen.invokeStatic(RT_TYPE, Method.getMethod("clojure.lang.ISeq arrayToList(Object[])"));
- } else {
- String cs = null;
- try {
- cs = RT.printString(value);
- //System.out.println("WARNING SLOW CODE: " + value.getClass() + " -> " + cs);
- } catch (Exception e) {
- throw new RuntimeException("Can't embed object in code, maybe print-dup not defined: " + value);
- }
- if (cs.length() == 0)
- throw new RuntimeException("Can't embed unreadable object in code: " + value);
-
- if (cs.startsWith("#<"))
- throw new RuntimeException("Can't embed unreadable object in code: " + cs);
-
- gen.push(cs);
- gen.invokeStatic(RT_TYPE, readStringMethod);
- partial = false;
- }
-
- if (partial) {
- if (value instanceof Obj && RT.count(((Obj)value).meta()) > 0) {
- gen.checkCast(IOBJ_TYPE);
- emitValue(((Obj)value).meta(), gen);
- gen.checkCast(IPERSISTENTMAP_TYPE);
- gen.invokeInterface(IOBJ_TYPE, Method.getMethod("clojure.lang.IObj withMeta(clojure.lang.IPersistentMap)"));
- }
- }
- }
+ void emitListAsObjectArray(Object value, GeneratorAdapter gen){
+ gen.push(((List) value).size());
+ gen.newArray(OBJECT_TYPE);
+ int i = 0;
+ for(Iterator it = ((List) value).iterator(); it.hasNext(); i++)
+ {
+ gen.dup();
+ gen.push(i);
+ emitValue(it.next(), gen);
+ gen.arrayStore(OBJECT_TYPE);
+ }
+ }
+
+ void emitValue(Object value, GeneratorAdapter gen){
+ boolean partial = true;
+ //System.out.println(value.getClass().toString());
+
+ if(value instanceof String)
+ {
+ gen.push((String) value);
+ }
+ else if(value instanceof Integer)
+ {
+ gen.push(((Integer) value).intValue());
+ gen.invokeStatic(Type.getType(Integer.class), Method.getMethod("Integer valueOf(int)"));
+ }
+ else if(value instanceof Double)
+ {
+ gen.push(((Double) value).doubleValue());
+ gen.invokeStatic(Type.getType(Double.class), Method.getMethod("Double valueOf(double)"));
+ }
+ else if(value instanceof Character)
+ {
+ gen.push(((Character) value).charValue());
+ gen.invokeStatic(Type.getType(Character.class), Method.getMethod("Character valueOf(char)"));
+ }
+ else if(value instanceof Class)
+ {
+ gen.push(((Class) value).getName());
+ gen.invokeStatic(Type.getType(Class.class), Method.getMethod("Class forName(String)"));
+ }
+ else if(value instanceof Symbol)
+ {
+ gen.push(((Symbol) value).ns);
+ gen.push(((Symbol) value).name);
+ gen.invokeStatic(Type.getType(Symbol.class),
+ Method.getMethod("clojure.lang.Symbol create(String,String)"));
+ }
+ else if(value instanceof Keyword)
+ {
+ emitValue(((Keyword) value).sym, gen);
+ gen.invokeStatic(Type.getType(Keyword.class),
+ Method.getMethod("clojure.lang.Keyword intern(clojure.lang.Symbol)"));
+ }
+ else if(value instanceof Var)
+ {
+ Var var = (Var) value;
+ gen.push(var.ns.name.toString());
+ gen.push(var.sym.toString());
+ gen.invokeStatic(RT_TYPE, Method.getMethod("clojure.lang.Var var(String,String)"));
+ }
+ else if(value instanceof IPersistentMap)
+ {
+ List entries = new ArrayList();
+ for(Map.Entry entry : (Set<Map.Entry>) ((Map) value).entrySet())
+ {
+ entries.add(entry.getKey());
+ entries.add(entry.getValue());
+ }
+ emitListAsObjectArray(entries, gen);
+ gen.invokeStatic(RT_TYPE,
+ Method.getMethod("clojure.lang.IPersistentMap map(Object[])"));
+ }
+ else if(value instanceof IPersistentVector)
+ {
+ emitListAsObjectArray(value, gen);
+ gen.invokeStatic(RT_TYPE, Method.getMethod(
+ "clojure.lang.IPersistentVector vector(Object[])"));
+ }
+ else if(value instanceof ISeq || value instanceof IPersistentList)
+ {
+ emitListAsObjectArray(value, gen);
+ gen.invokeStatic(Type.getType(java.util.Arrays.class),
+ Method.getMethod("java.util.List asList(Object[])"));
+ gen.invokeStatic(Type.getType(PersistentList.class),
+ Method.getMethod(
+ "clojure.lang.IPersistentList create(java.util.List)"));
+ }
+ else
+ {
+ String cs = null;
+ try
+ {
+ cs = RT.printString(value);
+ //System.out.println("WARNING SLOW CODE: " + value.getClass() + " -> " + cs);
+ }
+ catch(Exception e)
+ {
+ throw new RuntimeException(
+ "Can't embed object in code, maybe print-dup not defined: " +
+ value);
+ }
+ if(cs.length() == 0)
+ throw new RuntimeException(
+ "Can't embed unreadable object in code: " + value);
+
+ if(cs.startsWith("#<"))
+ throw new RuntimeException(
+ "Can't embed unreadable object in code: " + cs);
+
+ gen.push(cs);
+ gen.invokeStatic(RT_TYPE, readStringMethod);
+ partial = false;
+ }
+
+ if(partial)
+ {
+ if(value instanceof Obj && RT.count(((Obj) value).meta()) > 0)
+ {
+ gen.checkCast(IOBJ_TYPE);
+ emitValue(((Obj) value).meta(), gen);
+ gen.checkCast(IPERSISTENTMAP_TYPE);
+ gen.invokeInterface(IOBJ_TYPE,
+ Method.getMethod("clojure.lang.IObj withMeta(clojure.lang.IPersistentMap)"));
+ }
+ }
+ }
void emitConstants(GeneratorAdapter clinitgen){