diff --git a/build.xml b/build.xml index 1075c9b11b..031c2e669f 100644 --- a/build.xml +++ b/build.xml @@ -47,7 +47,8 @@ failonerror="true" fork="true"> - + + @@ -86,7 +87,8 @@ failonerror="true" fork="true"> - + + diff --git a/src/clj/clojure/core.clj b/src/clj/clojure/core.clj index e1aa2dfc1c..83b739b231 100644 --- a/src/clj/clojure/core.clj +++ b/src/clj/clojure/core.clj @@ -5707,8 +5707,12 @@ coercions will be done without overflow checks. Default: false." {:added "1.3"}) -(add-doc-and-meta *elide-meta* - "Bind to a collection of metadata keys to elide during compilation. +(add-doc-and-meta *compiler-options* + "A map of keys to options. + Note, when binding dynamically make sure to merge with previous value. + Supported options: + :elide-meta - a collection of metadata keys to elide during compilation. + :disable-locals-clearing - set to true to disable clearing, useful for using a debugger Alpha, subject to change." {:added "1.4"}) diff --git a/src/jvm/clojure/lang/Compile.java b/src/jvm/clojure/lang/Compile.java index 0def117571..6084bad1cc 100644 --- a/src/jvm/clojure/lang/Compile.java +++ b/src/jvm/clojure/lang/Compile.java @@ -14,6 +14,9 @@ import java.io.OutputStreamWriter; import java.io.PrintWriter; import java.io.IOException; +import java.util.ArrayList; +import java.util.Enumeration; +import java.util.Map; // Compiles libs and generates class files stored within the directory // named by the Java System property "clojure.compile.path". Arguments are @@ -25,13 +28,12 @@ public class Compile{ private static final String PATH_PROP = "clojure.compile.path"; private static final String REFLECTION_WARNING_PROP = "clojure.compile.warn-on-reflection"; private static final String UNCHECKED_MATH_PROP = "clojure.compile.unchecked-math"; -private static final String ELIDE_META_PROP = "clojure.elide.meta"; private static final Var compile_path = RT.var("clojure.core", "*compile-path*"); private static final Var compile = RT.var("clojure.core", "compile"); private static final Var warn_on_reflection = RT.var("clojure.core", "*warn-on-reflection*"); private static final Var unchecked_math = RT.var("clojure.core", "*unchecked-math*"); -private static final Var elide_meta = RT.var("clojure.core", "*elide-meta*"); +private static final Var compiler_options = RT.var("clojure.core", "*compiler-options*"); public static void main(String[] args) throws IOException{ @@ -50,14 +52,27 @@ public static void main(String[] args) throws IOException{ boolean warnOnReflection = System.getProperty(REFLECTION_WARNING_PROP, "false").equals("true"); boolean uncheckedMath = System.getProperty(UNCHECKED_MATH_PROP, "false").equals("true"); - Object elide = RT.readString(System.getProperty(ELIDE_META_PROP, "nil")); + + Object compilerOptions = null; + + for(Map.Entry e : System.getProperties().entrySet()) + { + String name = (String) e.getKey(); + String v = (String) e.getValue(); + if(name.startsWith("clojure.compiler.")) + { + compilerOptions = RT.assoc(compilerOptions + ,RT.keyword(null,name.substring(1 + name.lastIndexOf('.'))) + ,RT.readString(v)); + } + } try { Var.pushThreadBindings(RT.map(compile_path, path, warn_on_reflection, warnOnReflection, unchecked_math, uncheckedMath, - elide_meta, elide)); + compiler_options, compilerOptions)); for(String lib : args) { diff --git a/src/jvm/clojure/lang/Compiler.java b/src/jvm/clojure/lang/Compiler.java index e06bcdecd3..40cf01e84a 100644 --- a/src/jvm/clojure/lang/Compiler.java +++ b/src/jvm/clojure/lang/Compiler.java @@ -239,17 +239,23 @@ public class Compiler implements Opcodes{ static final public Var ADD_ANNOTATIONS = Var.intern(Namespace.findOrCreate(Symbol.intern("clojure.core")), Symbol.intern("add-annotations")); -//collection of keys -static final public Var ELIDE_META = Var.intern(Namespace.findOrCreate(Symbol.intern("clojure.core")), - Symbol.intern("*elide-meta*"), null).setDynamic(); +static final public Keyword disableLocalsClearingKey = Keyword.intern("disable-locals-clearing"); +static final public Keyword elideMetaKey = Keyword.intern("elide-meta"); + +static final public Var COMPILER_OPTIONS = Var.intern(Namespace.findOrCreate(Symbol.intern("clojure.core")), + Symbol.intern("*compiler-options*"), null).setDynamic(); + +static public Object getCompilerOption(Keyword k){ + return RT.get(COMPILER_OPTIONS.deref(),k); +} static Object elideMeta(Object m){ - Collection elides = (Collection) ELIDE_META.get(); + Collection elides = (Collection) getCompilerOption(elideMetaKey); if(elides != null) { for(Object k : elides) { - //System.out.println("Eliding:" + k + " : " + RT.get(m, k)); +// System.out.println("Eliding:" + k + " : " + RT.get(m, k)); m = RT.dissoc(m, k); } // System.out.println("Remaining: " + RT.keys(m)); @@ -5450,7 +5456,7 @@ public static class LocalBinding{ public final String name; public final boolean isArg; public final PathNode clearPathRoot; - public boolean canBeCleared = true; + public boolean canBeCleared = !RT.booleanCast(getCompilerOption(disableLocalsClearingKey)); public boolean recurMistmatch = false; public LocalBinding(int num, Symbol sym, Symbol tag, Expr init, boolean isArg,PathNode clearPathRoot)