Not logged in.  Login/Logout/Register | List snippets | | Create snippet | Upload image | Upload data

3290
LINES

< > BotCompany Repo | #759 // "Leading Edge" JavaX Translator (Extension of #7)

JavaX source code (desktop) [tags: use-pretranspiled] - run with: x30.jar

Download Jar. Uses 1176K of libraries. Click here for Pure Java version (35141L/234K).

!1006722

set flag callF_legacy.

// TODO: skip ifclass blocks in findFunctionInvocations.
//       after main loop completes (including standard functions+
//       classes), run tok_ifclass and if any change, run main loop
//       again.
//       This will allow clean handling of functions like "unnull"
//       which right now _always_ include Symbol (because unnull
//       references emptySymbol inside an ifclass Symbol block).

// Note: Before editing this, transpile #7
// Use 'Very fresh' (R-transpile doesn't seem to work) or Q/M if you haven't screwed yourself currently
// by making your transpiler unable to transpile itself... or
// something

// Note: Don't try hijackPrint, it doesn't seem to work in here
// (because of the way it is called by e.g. transpileForServer_returnPair?)

/* functions to possibly edit when creating/changing JavaX constructs:
  tok_pingify
*/

// new JavaParser includes
!include once #1025814
!include once #1025813

!include once #1025802 // optimized findCodeTokens

set flag OurSubLists.
set flag NoIllegalAccesses.

set flag javaTokForJFind_array_simpleCache.
set flag tok_moveImportsUp_skipMostReToks.

set flag findCodeTokens_quickIsIdentifier.
set flag findCodeTokens_quickIsInteger.

set flag AllowMetaCode.
set flag jreplace_performing. // record replacements

//set flag tok_forUnnull_debug.

// ifdef in cached includes? => i think cached includes still contain the ifdefs, so it's fine. tok_ifdef is not called within localStuff1

set flag noAI.
set flag isQuoted_dirty. // should be OK, we're dealing with tokens

static bool autoQuine = true;
static int maxQuineLength = 80;
sbool assumeTriple = true;
sbool quickInstanceOfEnabled; // interferes with things
sbool debug_jreplace;

sS mainSnippetID; // snippet to compile - for usePerProgramPreloads
sbool usePerProgramPreloads = true;

// _registerThread usually costs nothing because we need
// the registerWeakHashMap mechanism anyway for ping().
// Anyway - no forced functions for now :)
static L<S> functionsToAlwaysInclude = ll(
  //"_registerThread",
  //"asRuntimeException"
);

// classes with two type parameters that can written with just one
// e.g. Pair<S> => Pair<S, S>
static Set<S> pairClasses = lithashset("Pair", "Either", "Map", "AbstractMap", "HashMap", "TreeMap", "LinkedHashMap", "MultiMap", "CompactHashMap", "WrappedMap", "F1", "IF1", "AllOnAll", "AllOnAllWithUpdates", "MultiSetMap", "AutoMap", "ValueOnDemandMap", "NavigableMap", "SortedMap",
  "BijectiveMap", "PairCollector", "IF2_OOInt");

// classes with 3 type parameters that can written with just one
// e.g. T3<S> => T3<S, S, S>
static Set<S> tripleClasses = lithashset("T3", "IF2", "F2", "IVF3", "VF3");

sS transpilingSnippetID;
//static new AtomicInteger varCount;
static new ThreadLocal<AtomicInteger> varCountByThread;

static SS snippetCache = syncMap();

// Which snippets were actually requested during transpilation
static Set<S> cacheRequested;

// Which snippets were required when this program was last transpiled?
// (So we can preload them all.)
static Map<S, Set<S>> preloadsPerProgram = mruCache(500);

sbool useTokenIndexedList = true;
sbool opt_javaTok = true;
static bool cacheStdFunctions = true, cacheStdClasses = true;
static new HashMap<Long, CachedInclude> cachedIncludes;
static ExecutorService executor;
static SS standardClassesMap;
static long startTime, lastPrint;

// These variables have to be cleared manually for each transpilation

static new HashSet<Long> included;
static NavigableSet<S> definitions = ciSet();
static new HashMap<S> rewrites;
static new HashSet<S> shouldNotIncludeFunction; // this verifies after the fact that the function was not included
static new HashSet<S> shouldNotIncludeClass;
static new HashSet<S> doNotIncludeFunction; // this actually prevents the function from being included
static new SS functionToStaticHolder;
static new HashSet<S> doNotIncludeClass;
static new HashSet<S> needLatest; // this forces a function to be included
static new HashSet<S> addedFunctions;
static new HashSet<S> addedClasses;
static new HashSet<S> hardFunctionReferences;
static new HashSet<S> mapLikeFunctions;
static new HashSet<S> lambdaMapLikeFunctions;
static new HashSet<S> curry1LikeFunctions;
static new HashSet<S> mapMethodLikeFunctions;
static new HashSet<S> nuLikeFunctions;
static new HashSet<S> getLikeFunctions; // name is slightly misleading. this turns a pre-argument into a fieldLambda
static new HashSet<S> lambdaMethod0LikeFunctions; // we're getting better again with the names (maybe)
static new HashSet<S> lambda0LikeFunctions;
static new HashSet<S> lambda2LikeFunctions;
static SS extraStandardFunctions;
sbool quickmainDone1, quickmainDone2;
static new TreeSet<S> libs;
sS mainBaseClass, mainPackage, mainClassName;
sbool localStuffOnly; // for transpiling a fragment
sbool asInclude; // for transpiling an include (auto-close scopes, enable all standard class ifclass [todo])
sbool allowMetaCode = false; // run any embedded meta code
static LS metaPostBlocks, metaTransformers, localTransformers;
sbool dontPrintSource;

// disabling this because of the changed-include-early-in-standard-class problem
sbool dontLoadCachedIncludesFromVM = true;
sbool saveCachedIncludesInVM = false;

static new HashSet<S> haveClasses;

sclass CachedInclude {
  S javax;
  Future<S> java;
  S realJava;
  long snippetID;
  
  *() {}
  *(long *snippetID) {}
  
  S java() {
    ret realJava != null ? realJava : getFuture(java);
  }
  
  Future<S> javaFuture() {
    ret realJava != null ? nowFuture(realJava) : java;
  }
  
  void clean {
    if (java != null) {
      realJava = getFuture(java);
      java = null;
    }
  }
}

p {
  startTime = lastPrint = sysNow();
  pcall {
    if (!dontLoadCachedIncludesFromVM)
      vmKeepWithProgramMD5_get('cachedIncludes);
  }
  executor = Executors.newFixedThreadPool(numberOfCores());
  transpilingSnippetID = or(getThreadLocal((ThreadLocal<S>) getOpt(javax(), 'transpilingSnippetID)), transpilingSnippetID);
  //print(+transpilingSnippetID);
  set transpileRaw_dontCopyFromCreator;
  
  fO oldPrint = or(print_byThread()!, f print_raw);
  temp tempInterceptPrint(new F1<S, Bool>() {
    Bool get(S s) {
      long now = sysNow();
      long time = now-lastPrint; // -startTime;
      lastPrint = now;
      callF(oldPrint, "[" + formatInt(time/1000, 2) + ":" + formatInt(time % 1000, 3) + "] " + s);
      false;
    }
  });
  
  try {
    _main();
  } finally {
    interceptPrintInThisThread(oldPrint);
    if (executor != null) executor.shutdown();
    executor = null;
    localStuffOnly = false;
    asInclude = false;
  }
}

svoid _main() ctex {
  if (sameSnippetID(programID(), defaultJavaXTranslatorID())) setDefaultJavaXTranslatorID(#7);
  
  //reTok_modify_check = true;
  javaTok_opt = opt_javaTok;
  //findCodeTokens_indexed = findCodeTokens_unindexed = 0;
  findCodeTokens_bails = findCodeTokens_nonbails = 0;
  javaTok_n = javaTok_elements = 0;
  S in = loadMainJava();
  
  print("759 STARTING " + identityHashCode(main.class));
  
  if (usePerProgramPreloads && nempty(mainSnippetID)) {
    var preloads = preloadsPerProgram.get(fsI(mainSnippetID));
    print("Preloading " + nSnippets(preloads) + " for " + mainSnippetID);
    cachePreload(preloads);
  }
  
  // clear things
  cacheRequested = syncSet();
  includeInMainLoaded_magicComment = null;
  included.clear();
  definitions.clear();
  definitions.add("true");
  rewrites.clear();
  // XXX definitions.add("SymbolAsString");
  shouldNotIncludeFunction.clear();
  shouldNotIncludeClass.clear();
  doNotIncludeFunction.clear();
  functionToStaticHolder.clear();
  needLatest.clear();
  doNotIncludeClass.clear();
  addedFunctions.clear();
  addedClasses.clear();
  hardFunctionReferences.clear();
  mapLikeFunctions = cloneHashSet(tok_mapLikeFunctions());
  lambdaMapLikeFunctions = new HashSet;
  curry1LikeFunctions = new HashSet;
  mapMethodLikeFunctions = cloneHashSet(tok_mapMethodLikeFunctions());
  nuLikeFunctions.clear();
  getLikeFunctions.clear();
  lambdaMethod0LikeFunctions.clear();
  lambda0LikeFunctions.clear();
  lambda2LikeFunctions.clear();
  extraStandardFunctions = new HashMap;
  libs.clear();
  mainBaseClass = mainPackage = mainClassName = null;
  varCountByThread.set(null);
  quickmainDone1 = quickmainDone2 = false;
  metaPostBlocks = new L;
  metaTransformers = new L;
  localTransformers = new L;
  dontPrintSource = false;
  defaultMaxQuineLength_value = defaultMaxQuineLength_defaultValue;
  debug_jreplace = false;
  haveClasses.clear();
  
  //L ts = findTranslators(toLines(join(tok)));
  //print("Translators in source at start: " + structure(ts));
  
  L<S> tok = jtok(in);
  
  try {
    tok_definitions(tok);
    
    // add m { }
    
    if (!localStuffOnly && !hasCodeTokens(tok, "m", "{") && !hasCodeTokens(tok, "main", "{") && !hasCodeTokens(tok, "class", "main")) {
      if (l(tok) == 1) tok = singlePlusList(first(tok), dropFirst(javaTok("m {}")));
      else {
        replaceTokens_reTok(tok, 1, 2, "m {\n\n" + unnull(get(tok, 1)));
        replaceTokens_reTok(tok, l(tok)-2, l(tok)-1, unnull(get(tok, l(tok)-2)) + "}");
      }
      tok_moveImportsUp(tok);
    }
    
    // standard translate
    
    //ts = findTranslators(toLines(join(tok)));
    //print("Translators in source: " + structure(ts));
    
    if (tok_hasTranslators(tok)) {
      print("DEFAULT TRANSLATE");
      tok = jtok(defaultTranslate(join(tok)));
    }
    
    //print("end of default translate");
    //print(join(tok));
  
    //tok_autoCloseBrackets(tok);    
    
    tok_metaTransformNow(tok);
    
    tok_processEarlyIncludes(tok);
      
    tok_earlyGeneralStuff(tok);
    
    tok = tok_processIncludes(tok); // before standard functions
    if (processConceptsDot(tok))
      tok = tok_processIncludes(tok);
    tok = localStuff1(tok);
    
   if (!localStuffOnly) {
    int safety = 0;
    boolean same;
    do { // BIG LOOP
      ping();
      LS before = cloneList(tok);
      
      // do the non-local stuff (flags and rewrites, things that correlate across includes like tok_selfType)
      
      // to allow crazy stuff like "nonStatic !include #someStaticClass"
      tok_processEarlyIncludes(tok);
      
      jreplace(tok, "nonStatic static", "");
      
      tok_selfType(tok);
      tok_mainClassNameAndPackage(tok);
      tok_definitions(tok);
      tok_ifndef(tok);
      tok_ifdef(tok, l1 isDefined);
      defineMapLikesEtc(tok);
      if (tok_applyAllXLikeFunctions(tok)) {
        functionReferences(tok);
        lambdaReferences(tok);
      }
      
      tok_dropExtraCommas(tok); // from e.g. tok_applyMapMethodLikeFunctions
      //tok_delegateTo(tok);
      //tok_replaceWith(tok);
      tok_findAndClearRewrites(tok);
      tok_processRewrites(tok);
      
      //tok_multiTypeArguments_v2(tok);
      
      // main bla(...) => mainClassName.bla(...)
      // or main ClassName => main.ClassName
      //jreplace(tok, "main <id>(", mainClassName() + ".$2(");
      grabImportedStaticFunctions(tok);
      jreplace_dyn_allowNull(tok, "main <id>", (_tok, cIdx, end) -> {
        S fname = _tok.get(cIdx+2);
        bool isClass = haveClasses.contains(fname);
        //printVars expandMainRef(+fname, +isClass);
        if (isClass || eqGet(_tok, cIdx+4, "(")) {
          S holder = functionToStaticHolder.get(fname);
          //printVars expandMainRef(+holder);
          S call = "." + fname;
          ret or(holder, mainClassName()) + call;
        }
        null;
      });
      
      // references to global function holder
      jreplace_dyn_allowNull(tok, "mainFunctionHolder <id>", (_tok, cIdx, end) -> {
        S fname = _tok.get(cIdx+2);
        S holder = functionToStaticHolder.get(fname);
        ret or(holder, mainClassName()) + ".class";
      });
      
      try {
        if (safety == 0) tok = quickmain(tok);
      } catch e {
        printSources(tok);
        rethrow(e);
      }
      tok_collectMetaPostBlocks(tok, metaPostBlocks);
      tok_collectTransformers(tok, metaTransformers);
      tok_collectTransformers(tok, localTransformers, "meta-transformLocal");

      tok_metaTransformNow(tok);
      
      // Hack to allow DynModule to reimplement _registerThread
      /*if (tok.contains("DynModule") && !addedClasses.contains("DynModule"))
        addStandardClasses_v2(tok);*/
      
      defineExtraSF(tok);
      tok = standardFunctions(tok);
      tok = stdstuff(tok); // all the keywords, standard
      S diff;
      long startTime = now();
      //diff = unidiff(before, join(tok));
      //print("unidiff: " + (now()-startTime) + " ms");
      //same = eq(diff, "");
      same = eq(tok, before);
      if (!same) {
        print("Not same " + safety + ".");
        //print(indent(2, diff));
      }
      if (safety++ >= 10) {
        //print(unidiff(before, join(tok)));
        printSources(tok);
        fail("safety 10 error!");
      }
    } while (!same); // END OF BIG LOOP
    
    print("Post.");
    
    if (mainBaseClass != null) {
      jreplace1(tok, "class main", "class main extends " + mainBaseClass);
      mainBaseClass = null;
    }
    
    print('moveImportsUp); tok_moveImportsUp(tok);
    
    print('Indexing); tok = indexTokenList(tok);
    
    // POST-PROCESSING after stdstuff loop
    
    if (transpilingSnippetID != null)
      jreplace_dyn(tok, "class whatever", 
        func(L<S> tok, int cIndex) -> S {
          pcall { ret "class " + stringToLegalIdentifier(getSnippetTitle(transpilingSnippetID)); }
          ret "class Whatever";
        });
    
    tok_elegantVSInlined(tok);
    
    print('extendClasses); tok = extendClasses(tok);
    print('libs); libs(tok);
    print('sourceCodeLine); sourceCodeLine(tok);
    
    tok_overridableFunctionDefs(tok, null);
    
    // escaping for lambdas
    //jreplace(tok, "-=>", "->");
  
    // Stuff that depends on the list of inner classes (haveClasses)
    haveClasses = haveClasses_actual(tok);
    print('innerClassesVar); innerClassesVar(tok, haveClasses);
    fillVar_transpilationDate(tok);
    haveClasses_addImported(tok, haveClasses);
    print('ifclass); tok_ifclass(tok, haveClasses);
    
    print('slashCasts); slashCasts(tok, haveClasses);
    print('newWithoutNew); newWithoutNew(tok, haveClasses);
    
    if (!assumeTriple) {
      print('Triple);
      if (tok.contains("Triple") && !haveClasses.contains("Triple")) {
        jreplace(tok, "Triple", "T3");
        haveClasses.remove("Triple");
        haveClasses.add("T3");
        slashCasts(tok, lithashset("T3"));
        tok_quickInstanceOf(tok, lithashset("T3"));
      }
    }
    
    if (hasDef("SymbolAsString"))
      jreplace(tok, "Symbol", "String");
  
    // using non-lazy version now for cleanImports
    print('classReferences); expandClassReferences/*_lazy*/(tok, haveClasses);
    
    if (metaCodeAllowed()) runMetaPostBlocks(tok);

    // Error-checking
    print("Error-checking"); 
    Set<S> functions = new HashSet(findFunctions(tok));
    for (S f : hardFunctionReferences)
      if (!functions.contains(f))
        warn("Function " + f + " requested, but not supplied");
  
    print('autoImports); tok = autoImports(tok); // faster to do it at the end
    
    if (hasDef("cleanImports"))
      tok_cleanImports(tok);
    
    if (includeInMainLoaded_magicComment != null) {
      int i = lastIndexOfStartingWith(tok, includeInMainLoaded_magicComment);
      if (i >= 0) tok.set(i, dropPrefix(includeInMainLoaded_magicComment, tok.get(i)));
    }

    print("definitions=" + sfu(definitions));
    if (containsOneOf(definitions, "allpublic", "reparse", "PublicExceptTopClass")) {
      // Fire up the Java parser & pretty printer!
      print(containsIC(definitions, "allpublic")? "Making all public." : "Reparsing.");
      //try {
        S src = join(tok);
        try {
          if (containsIC(definitions, "allpublic"))
            src = javaParser_makeAllPublic(src);
          else if (containsIC(definitions, "PublicExceptTopClass"))
            src = javaParser_makeAllPublic(src, notTopLevelClassDecl := true);
          else if (containsIC(definitions, "keepComments"))
            src = javaParser_makeAllPublic_keepComments(src);
          else {
            print("javaParser_reparse_keepComments. size=" + l(src));
            src = javaParser_reparse_keepComments(src);
            print("size=" + l(src));
          }
        } catch e {
          S _src = src;
          S errorContext = extractAndPrintJavaParseError(_src, e);
          File f = transpilerErrorSourceFile();
          saveTextFileVerbose(f, src);
          dontPrintSource = true;
          fail("Java parsing error:" + errorContext + innerMessage(e)); // drop the long nested parser stacktraces
        }
        tok = jtok(src);
      /*} catch e {
        S src = join(tok);
        if (!dontPrintSource)
          print(src);
        print(f2s(saveProgramTextFile("error.java", src)));
        throw rethrow(e);
      }*/
    }
    
    // Do this after JavaParser (because it doesn't like package after class)
    
    if (mainPackage != null) {
      print('mainPackage);
      tokPrepend(tok, 1, "package " + mainPackage + ";\n");
      reTok(tok, 1, 2);
    }
    
    if (mainClassName != null) {
      print('mainClassName);
      jreplace(tok, "class main", "class " + mainClassName);
      jreplace(tok, "main.class", mainClassName + ".class");
      //tokPrepend(tok, 1, "class main {}\n"); // so main.class is generated and compiler sanity checks succeed. we can later skip it in the JavaXClassLoader
    }
    
    if (nempty(libs)) {
      print("Adding libs: " + libs);
      tok.add(concatMap_strings(func(S s) -> S { "\n!" + s }, libs));
    }
   } // if (!localStuffOnly)
  } catch e {
    if (!dontPrintSource)
      printSources(tok);
    S src = join(tok);
    print(f2s(saveProgramTextFile("error.java", src)));
    throw rethrow(e);
  }
  
  print("Saving.");
  
  // for dexcompile.php
  if (mainClassName != null)
    tokPrepend(tok, 0, "//FILENAME: " 
      + (mainPackage != null ? mainPackage.replace(".", "/") + "/" : "") + mainClassName + ".java\n");
    
  if (mainJava != null)
    mainJava = join(tok);
  else if (tok.contains("package"))
    splitJavaFiles(tok);
  else
    saveMainJava(tok);
    
  if (usePerProgramPreloads && nempty(mainSnippetID))
    preloadsPerProgram.put(fsI(mainSnippetID), cacheRequested);
}

static LS localStuff1(LS tok) {
  int safety = 0, i;
  boolean same;
  tok = indexTokenList(tok);
  
  tok_scopes(tok, autoCloseScopes := true);
    
  do {
    ping();
    LS before = cloneList(tok);
    
    //print("localStuff loop " + safety);
    
    earlyStuff(tok);
    
    // EARLY local stuff goes here
    
    tok_dropMetaComments(tok);
    
    tok_earlyGeneralStuff(tok);
    
    conceptDeclarations(tok);
    tok_recordDecls(tok);
    
    tok = multilineStrings(tok);
    tok_singleQuoteIdentifiersToStringConstants(tok);
    tok_inStringEvals(tok);
    tok_listComprehensions(tok);
    
    tok_eventInterfaces(tok);
    
    tok_eventFunctions(tok);
    
    tok_for_single(tok);
    
    tok_for_unpair(tok); // Do this...
    //tok_doubleFor_v2(tok);
    tok_doubleFor_v3(tok); // ...before this
    
    tok_forUnnull(tok);
    tok_ifCast(tok);
    forPing(tok);
    tok_directSnippetRefs(tok);
    quicknu(tok);
    //tok_juxtaposeCalls(tok);
    
    tok_castQuestionDot(tok);
    
    jreplace(tok, "LLS", "L<LS>");
    jreplace(tok, "LS", "L<S>");
    jreplace(tok, "LByte", "L<Byte>");
    jreplace(tok, "ES", "Ext<S>");
    jreplace(tok, "ExtS", "Ext<S>");
    jreplace(tok, "ClS", "Cl<S>");
    
    jreplace(tok, "WeakRef", "WeakReference");
    
    jreplace(tok, "dispose <id>;", "{ cleanUp($2); $2 = null; }");
  
    tok_doPing(tok);
      
    replaceKeywordBlock(tok,
      "androidUI",
      "{ androidUI(r {",
      "}); }");
      
    replaceKeywordBlock(tok,
      "withDBLock",
      "{ withDBLock(r {",
      "}); }");
      
    replaceKeywordBlock(tok, "afterwards", "temp tempAfterwards(r {", "});");
      
    for (S keyword : ll("tokcondition", "tokCondition"))
      replaceKeywordBlock(tok,
        keyword,
        "new TokCondition { public bool get(final L<S> tok, final int i) {",
        "}}");
      
    jreplace(tok, "synced <id>", "synchronized $2");
    jreplace(tok, "sync <id>", "synchronized $2");
    
    jreplace(tok, "synchronized {", "synchronized(this) {");
    
    replaceKeywordBlock(tok, "answer",
      "static S answer(S s) {\nfinal new Matches m;\n",
      "\nret null;\n}");
      
    replaceKeywordBlock(tok, "static-pcall",
      "static { pcall {",
      "}}");
      
    replaceKeywordBlock(tok, "loading",
      "{ temp tempShowLoadingAnimation(); ",
      "}");
  
    replaceKeywordPlusQuotedBlock(tok, "loading",
      new O { S[] get(L<S> tok, int i) {
        S text = tok.get(i+2);
        ret new S[] {
          "{ temp tempShowLoadingAnimation(" + text + "); ",
          "}" };
      }});
      
    while ((i = jfind(tok, "visualize as")) >= 0) {
      int j = tok_findEndOfStatement(tok, i); // expression, rather
      tok.set(i+2, "{ ret");
      tok.set(j-1, "; }");
      reTok(tok, i, j);
    }
      
    for (S pat : ll("visual {", "visualize {"))
      jreplace(tok, pat, "public JComponent visualize() {", tokCondition_beginningOfMethodDeclaration());
      
    jreplace(tok, "cachedVisualize {",
      //"public transient simplyCached JComponent visualize() {");
      "public transient simplyCached JComponent visualize() { ret markVisualizer(this, visualize_impl()); }\n"
      + "JComponent visualize_impl() {");
  
    jreplace(tok, "visualize2 {", "JComponent visualize2() {", tokCondition_beginningOfMethodDeclaration());
    
    replaceKeywordBlock(tok, "start-thread-printDone", "start-thread {", "printDone(); }");

    replaceKeywordBlock(tok, "start-thread", [[start { thread "Start" { temp enter(); pcall {]], "}}}");
    
    jreplace(tok, "start {", "void start() ctex { super.start();", tokCondition_beginningOfMethodDeclaration());
    
    var notVoidMethod = tokcondition {
      ret neqGet(tok, i-1, "void");
    };
    
    // run { ... } => public void run() { ... }
    // same with close
    // These need to be ctex as AutoCloseable and Runnable don't allow explicit exceptions
    jreplace(tok, "run {", "public void run() ctex {", notVoidMethod);
    jreplace(tok, "close {", "public void close() ctex {", notVoidMethod);
    
    replaceKeywordBlock(tok, "html",
      "static O html(S uri, fMap<S, S> params) ctex " + "{\n", "}");
    
    replaceKeywordBlock(tok, "afterVisualize",
      "visualize { JComponent _c = super.visualize();",
      "ret _c; }");
    
    replaceKeywordBlock(tok, "enhanceFrame",
      "void enhanceFrame(Container f) { super.enhanceFrame(f);",
      "}");
    
    if (assumeTriple)
      jreplace(tok, "Triple", "T3");

    tok_shortFinals(tok);
    
    tok_moduleClassDecls(tok);

    jreplace(tok, "static sync", "static synchronized");
    jreplace(tok, "sclass", "static class");
    jreplace(tok, "fclass", "final class");
    jreplace(tok, "fsclass", "final static class");
    jreplace(tok, "srecord", "static record");
    jreplace(tok, "strecord", "static transformable record");
    jreplace(tok, "record noeq", "noeq record");
    jreplace(tok, "asclass", "abstract static class");
    jreplace(tok, "sinterface", "static interface");
    jreplace(tok, "ssynchronized", "static synchronized");
  
    jreplace(tok, "ssvoid", "static synchronized void");
    jreplace(tok, "sbool", "static bool");
    jreplace(tok, "fbool", "final bool");
    jreplace(tok, "sint", "static int");
    jreplace(tok, "snew", "static new");
    jreplace(tok, "sv <id>", "static void $2");
    jreplace(tok, "pvoid", "public void");
  
    // "sS" => static S
    jreplace(tok, "sS", "static S");
  
    // "sO" => static O
    jreplace(tok, "sO", "static O");
  
    // "sL" => static L
    jreplace(tok, "sL", "static L");
  
    // "toString {" => "public S toString() {"
    jreplace(tok, "toString {", "public S toString() {");
    
    jreplace(tok, "Int", "Integer");
    jreplace(tok, "Bool", "Boolean");
    jreplace(tok, "BigInt", "BigInteger");
    jreplace(tok, "Char", "Character");
    
    jreplace(tok, "Sym", "Symbol");
    jreplace(tok, "SymSym", "SymbolSymbol");
    
    jreplace(tok, "SS", "Map<S>");
    jreplace(tok, "SymbolSymbol", "Map<Symbol>");
    
    jreplace(tok, "CISet", "Set<S>");
    
    jreplace(tok, "MapSO", "Map<S, O>");
    
    jreplace(tok, "ByName<", "IF1<S, ");
    
    jreplace(tok, "ITransform<<id>>", "IF1<$3>");
    jreplace(tok, "ITransform", "IF1");
    
    jreplace(tok, "PairS", "Pair<S>");
    jreplace(tok, "LPairS", "L<Pair<S>>");
    
    jreplace(tok, "T3S", "T3<S>");
    jreplace(tok, "F1S", "F1<S>");
    
    jreplace(tok, "ItIt", "IterableIterator");
    jreplace(tok, "CloseableItIt", "CloseableIterableIterator");

    // ">" instead of "extends"
    
    for (S keyword : ll("class", "interface")) {
      jreplace(tok, "\*keyword*/ <id> > <id>", "$1 $2 extends $4", tokCondition {
        S t = _get(tok, i+1+4*2);
        ret eq(t, "{") || isIdentifier(t);
      });
      jreplace(tok, "\*keyword*/ <id> > <id><<id>> {", "$1 $2 extends $4  $5 $6 $7 {");
      jreplace(tok, "\*keyword*/ <id><<id>> > <id>", "$1 $2<$4> extends $7");
    }
    
    jreplace(tok, "ISegmenter", "IF1<BufferedImage, L<Rect>>");
    
    // IPred<A, B> => IF2<A, B, Bool>
    jreplace(tok, "IPred<<id>, <id>>", "IF2<$3, $5, Bool>");
    
    // IPred<A> => IF1<A, Bool>
    jreplace(tok, "IPred<<id>>", "IF1<$3, Bool>");
    jreplace(tok, "IPred<<id>[]>", "IF1<$3[], Bool>");
    
    // Proposition => WithReasoning<S> (should we really define this?)
    jreplace("Proposition", "WithReasoning<S>");
    
    replaceKeywordBlock(tok, "print exceptions",
      "{ try {",
      "} on fail __e { printStackTrace(__e); } }");
    
    // "on fail {" => "catch (Throwable _e) { ... rethrow(_e); }"
    replaceKeywordBlock(tok, "on fail",
      "catch (Throwable _e) {",
      "\nthrow rethrow(_e); }");
  
    // "on fail e {" => "catch (Throwable e) { ... rethrow(e); }"
    replaceKeywordBlock_dyn2_legacy(tok, "on fail <id>", new O {
      S[] get(LS tok, int iOpening, int iClosing) {
        S var = tok.get(iOpening-2);
        ret new S[] {
          "catch (Throwable " + var + ") {",
          "\nthrow rethrow(" + var + "); }"
        };
      }
    });

    // "on fail Type e {" => "catch (Type e) { ... rethrow(e); }"
    replaceKeywordBlock_dyn2_legacy(tok, "on fail <id> <id>", new O {
      S[] get(LS tok, int iOpening, int iClosing) {
        S type = tok.get(iOpening-4);
        S var = tok.get(iOpening-2);
        ret new S[] {
          "catch (" + type + " " + var + ") {",
          "\nthrow " + var + "; }"
        };
      }
    });

    // "catch {" => "catch (Throwable _e) {"
    jreplace(tok, "catch {", "catch (Throwable _e) {");
  
    jreplace_dyn(tok, "catch print {", -> {
      S var = makeVar();
      ret "catch \*var*/ { printStackTrace(\*var*/);";
    });
  
    // "catch print e {" => "catch e { printStackTrace(e); "
    jreplace(tok, "catch print <id> {", "catch $3 { printStackTrace($3);");
  
    // "catch print short e {" => "catch e { printExceptionShort(e); "
    jreplace(tok, "catch print short <id> {", "catch $4 { printExceptionShort($4);");
    
    // "catch X e {" => "catch (X e) {"
    jreplace(tok, "catch <id> <id> {", "catch ($2 $3) {");
  
    // "catch e {" => "catch (Throwable e) {" (if e is lowercase)
    jreplace(tok, "catch <id> {", "catch (Throwable $2) {", tokcondition {
      S word = tok.get(i+3);
      ret startsWithLowerCaseOrUnderscore(word);
    });
    
    jreplace(tok, "+ +", "+", tokcondition {
      //printStructure("++: ", subList(tok, i-1, i+6));
      if (empty(_get(tok, i+2))) ret false; // no space between the pluses
      if (empty(_get(tok, i)) && eq("+", _get(tok, i-1))) ret false;  // an actual "++" at the left
      if (empty(_get(tok, i+4)) && eq("+", _get(tok, i+5))) ret false;  // an actual "++" at the right
      //print("doing it");
      ret true;
    });
  
    // single underscore (not allowed in Java anymore) to double underscore
    jreplace(tok, "_", "__");
    
    // [stdEq] -> implementation of equals() and hashCode()
    jreplace(tok, "[stdEq]",
      "public bool equals(O o) { ret stdEq2(this, o); }\n" +
      "public int hashCode() { ret stdHash2(this); }");
    
    // [stdToString] -> toString { ret stdToString(this); }
    jreplace(tok, "[stdToString]",
      "toString { ret stdToString(this); }");
    
    jreplace(tok, "for (<id> :", "for (var $3 :");
    
    jreplace(tok, "for (<id> <id>)", "for ($3 $4 : list($3))");
    jreplace(tok, "for (final <id> <id>)", "for (final $4 $5 : list($4))");

    tok_retShortForReturn(tok);
    
    // "continue unless", "break unless"
    
    for (S phrase : ll("continue unless", "break unless"))
      while ((i = jfind(tok, phrase)) >= 0) {
        S keyword = tok.get(i);
        int j = scanOverExpression(tok, getBracketMap(tok), i+4, ";");
        replaceTokens(tok, i, i+4, "{ if (!(");
        tok.set(j, ")) " + keyword + "; }");
        reTok(tok, i, j+1);
      }
    
    // S s = bla(), return if null; => S s = bla(); if (s == null) return;
    // same with continue, break
    while ((i = jfind(tok, ", <id> if null;", tokCondition {
      ret eqOneOf(tok.get(i+3), "return", "ret", "continue", "break");
    })) >= 0) {
      S cmd = tok.get(i+2);
      int j = tok_findBeginningOfStatement(tok, i);
      print("Found statement " + j + "/" + i + " - " + joinSubList(tok, j-1, i+5*2-1));
      S var = getVarDeclarationName(subList(tok, j-1, i));
      replaceTokens_reTok(tok, i, i+5*2-1, "; if (" + var + " == null) " + cmd + ";");
    }
    
    // S s = bla(), return false if null; => S s = bla(); if (s == null) return false;
    // (with false being any identifier)
    while ((i = jfind(tok, ", return <id> if null;")) >= 0) {
      S returnValue = tok.get(i+4);
      int j = tok_findBeginningOfStatement(tok, i);
      S var = getVarDeclarationName(subList(tok, j-1, i));
      replaceTokens_reTok(tok, i, i+6*2-1, "; if (" + var + " == null) return " + returnValue + ";");
    }
    
    // "continue if", "break if"
    
    for (S phrase : ll("continue if", "break if"))
      while ((i = jfind(tok, phrase)) >= 0) {
        S keyword = tok.get(i);
        int j = scanOverExpression(tok, getBracketMap(tok), i+4, ";");
        replaceTokens(tok, i, i+4, "{ if (");
        tok.set(j, ") " + keyword + "; }");
        reTok(tok, i, j+1);
      }
    
    // return unless set <var>; => { if (var) return; set var; }
    jreplace(tok, "return unless set <id>;", "{ if ($4) return; set $4; }");

    // set x; => x = true;
    // yeah it doesn't save many characters, but I like it
    jreplace(tok, "set <id>;", "$2 = true;", tokCondition {
      ret !eqGet(tok, i-1, "unless");
    });
    
    // set !x; => x = false; (did this one day and thought yes it makes sense in a way)
    jreplace(tok, "set !<id>;", "$3 = false;");
    
    // unset x; => x = false;
    jreplace(tok, "unset <id>;", "$2 = false;");
    
    // "return if"
    
    while ((i = jfind(tok, "return if")) >= 0) {
      int j = scanOverExpression(tok, getBracketMap(tok), i+4, ";");
      replaceTokens(tok, i, i+4, "{ if (");
      tok.set(j, ") return; }");
      reTok(tok, i, j+1);
    }
    
    // "return unless"
    
    while ((i = jfind(tok, "return unless")) >= 0) {
      int j = scanOverExpression(tok, getBracketMap(tok), i+4, ";");
      replaceTokens(tok, i, i+4, "{ if (!(");
      tok.set(j, ")) return; }");
      reTok(tok, i, j+1);
    }
    
    tok_ifNullAssign(tok);

    // "return <id> if"
    
    // "return with <statement>" / "continue with <statement>" / "break with <statement>"
    
    while ((i = jfind(tok, "<id> with", tokcondition { ret eqOneOf(tok.get(i+1), "return", "continue", "break"); })) >= 0) {
      // XXX int j = scanOverExpression(tok, getBracketMap(tok), i+4, ";");
      int j = tok_findEndOfStatement(tok, i+4)-1;
      //print("Found statement: " + joinSubList(tok, i+4, j+1));
      tok.set(j, "; " + tok.get(i) + "; }");
      replaceTokens(tok, i, i+3, "{");
      reTok(tok, i, j+1);
    }
    
    while ((i = jfind(tok, "return <id> if")) >= 0) {
      int j = scanOverExpression(tok, getBracketMap(tok), i+4, ";");
      tok.set(j, ") return " + tok.get(i+2) + "; }");
      replaceTokens(tok, i, i+6, "{ if (");
      reTok(tok, i, j+1);
    }
    
    // return "bla" with <statement>
    
    while ((i = jfindOneOf(tok,
      "return <quoted> with", "return <id> with")) >= 0) {
      S result = tok.get(i+2);
      int j = scanOverExpression(tok, getBracketMap(tok), i+6, ";");
      replaceTokens(tok, i, i+5, "{");
      tok.set(j, "; return " + result + "; }");
      reTok(tok, i, j+1);
    }
    
    tok_debugStatements(tok);

    // while not null (...) / if not null (...)
    
    while ((i = jfind_check not(tok, "<id> not null (", tokcondition {
      ret eqOneOf(_get(tok, i+1), "if", "while");
    })) >= 0) {
      int closingBracket = findEndOfBracketPart(tok, i+6)-1;
      replaceTokens(tok, i+2, i+6, "(");
      tok.set(closingBracket, ") != null)");
      reTok(tok, i, closingBracket+1);
    }
    
    // while null (...) / if null (...)
    
    while ((i = jfind_check null(tok, "<id> null (", tokcondition {
      ret eqOneOf(_get(tok, i+1), "if", "while");
    })) >= 0) {
      int closingBracket = findEndOfBracketPart(tok, i+4)-1;
      replaceTokens(tok, i+2, i+4, "(");
      tok.set(closingBracket, ") == null)");
      reTok(tok, i, closingBracket+1);
    }
    
    // Replace $1 with m.unq(0) etc. - caveat: this blocks identifiers $1, $2, ...
    for (i = 1; i < l(tok); i += 2) {
      S s = tok.get(i);
      if (s.startsWith("$")) {
        s = substring(s, 1);
        if (isInteger(s)) {
          tok.set(i, "m.unq(" + (parseInt(s)-1) + ")");
          reTok(tok, i);
        }
      }
    }
  
    // instanceof trickery
    
    jreplace(tok, "is a <id>", "instanceof $3");
    jreplace(tok, "!<id> instanceof <id>.<id>", "!($2 instanceof $4.$6)");
    jreplace(tok, "!<id> instanceof <id>", "!($2 instanceof $4)");
    jreplace(tok, "<id> !instanceof <id>", "!($1 instanceof $4)");
    
    // map func1 func2 func3(...) => mapFGH(f func1, f func2, f func3, ...)
    jreplace(tok, "map <id> <id> <id>(", "mapFGH(f $2, f $3, f $4,");

    // map func1 func2(...) => mapFG(f func1, f func2, ...)
    jreplace(tok, "map <id> <id>(", "mapFG(f $2, f $3,");

    // "ref->bla" for dereferencing Concept.Ref or ThreadLocal or other
    // For lambdas, use SPACES on the left or right of the arrow!
    //jreplace(tok, "<id> ->", "$1.get().");
    jreplace(tok, "->", ".get().", tokcondition {
      ret empty(tok.get(i)) // no space on left of arrow
        && empty(tok.get(i+2)) // no space inside of arrow
        && empty(tok.get(i+4)) // no space on right of arrow
        && !eq(_get(tok, i-1), "-"); // i-->0;
    });
    
    // shortened subconcept declaration (before star constructors!)
    shortenedSubconcepts(tok);
    
    tok_beaConceptDecls(tok);
    
    // "case" as a variable name ( => _case)
    
    caseAsVariableName(tok);
    
    // "do" as a function name ( => dO)
    
    tok_doAsMethodName(tok);
    
    // "continue" as a function name ( => _continue)
    continueAsFunctionName(tok);
    
    tok_extend(tok);
    
    jreplace(tok, "pn {", "p-noconsole {");
      
    // Do these BEFORE awt replacement! ("p-awt" contains "awt" token)
    replaceKeywordBlock(tok, "r-awt", "r { awt {", "}}");
    if (hasCodeTokens(tok, "p", "-")) tok_p_old(tok);

    replaceKeywordBlock(tok, "awt-messagebox", "awt { pcall-messagebox {", "}}");
    replaceKeywordBlock(tok, "awt", "swingLater(r {", "});");
  
    jreplace(tok, "p-android {", "set flag Android. p {");
      
    unswing(tok);
    lockBlocks(tok);
    tok_switchTo(tok);
    
    // trim x;
    
    jreplace(tok, "trim <id>;", "$2 = trim($2);");
  
    // iterate with index
  
    tok_forOver(tok);
    
    jreplace (tok, "for <id> to <id>:", "for (int $2 = 0; $2 < $4; $2++)");
    jreplace (tok, "for <id> to <int>:", "for (int $2 = 0; $2 < $4; $2++)");
    
    tok = expandShortTypes(tok);
      
    tok_equalsCast(tok);
    tok_equalsOptCast(tok);

    replaceKeywordBlock(tok, "r-thread-messagebox", "r-thread { pcall-messagebox {", "}}");
    
    replaceKeywordBlock(tok, "thread-messagebox", "thread { pcall-messagebox {", "}}");
    
    jreplace(tok, "rThread {", "r-thread {");
    jreplace(tok, "rEnterThread {", "rThreadEnter {");
    jreplace(tok, "rThreadEnter {", "r-thread { temp enter(); ");
  
    replaceKeywordBlock(tok, "r-thread", "runnableThread(r {", "})");
    rNamedThread(tok);
    
    // only works in the scope of a DynModule
    jreplace(tok, "rEnter {", "r { temp enter(); ");
  
    replaceKeywordBlock(tok, "r-pcall", "r { pcall {", "}}");
  
    replaceKeywordBlock(tok, "r-messagebox", "r { pcall-messagebox {", "}}");
    
    jreplace(tok, "r <id> + r <id>", "r { $2(); $5(); }");
    
    // runnable and r - now also with automatic toString if enabled
    for (S keyword : ll("runnable", "r")) {
      while ((i = jfind(tok, keyword + " {")) >= 0) {
        int idx = findCodeTokens(tok, i, false, "{");
        int j = findEndOfBracketPart(tok, idx);
        L<S> contents = subList(tok, idx+1, j-1);
        replaceTokens(tok, i, j+1, "new Runnable {"
          + "  public void run() ctex { " + tok_addSemicolon(contents) + "\n}"
          + (autoQuine ? tok_autoQuineFunc(contents) : "")
          + "}");
        reTok(tok, i, j+1);
      }
      
      while ((i = jfind(tok, keyword + " <quoted> {")) >= 0) {
        int idx = findCodeTokens(tok, i, false, "{");
        int j = findEndOfBracketPart(tok, idx);
        L<S> contents = subList(tok, idx+1, j-1);
        replaceTokens(tok, i, j+1, "new Runnable {"
          + "  public void run() ctex { " + tok_addSemicolon(contents) + "\n}"
          + "  toString { ret " + tok.get(i+2) + "; }"
          + (autoQuine ? tok_autoQuineFunc(contents, '_shortenedSourceCode) : "")
          + "}");
        reTok(tok, i, j+1);
      }
    }
    
    replaceKeywordBlock(tok,
      "expectException",
      "{ bool __ok = false; try {",
      "} catch { __ok = true; } assertTrue(\"expected exception\", __ok); }");
      
    while ((i = tok.indexOf("tex")) >= 0) {
      tok.set(i, "throws Exception");
      tok = jtok(tok);
    }
    
    // shorter & smarter whiles
    
    jreplace(tok, "while true", "while (true)");
    jreplace(tok, "while licensed", "while (licensed())");
    jreplace(tok, "repeat {", "while (licensed()) {");
    tok_repeatWithSleep(tok);
    
    // null; => return null; etc.
  
    O cond = tokcondition {
      ret tok_tokenBeforeLonelyReturnValue(tok, i-1);
    };
    jreplace(tok, "null;", "return null;", cond);
    jreplace(tok, "false;", "return false;", cond);
    jreplace(tok, "true;", "return true;", cond);
    jreplace(tok, "this;", "return this;", cond);
    
    // ok <cmd> => ret "OK" with <cmd> [probably outdated]
    jreplace(tok, "ok <id>", "return \"OK\" with $2",
      (_tok, nIdx) ->
        !eqGetOneOf(_tok, nIdx+3, "aka"));
    replaceKeywordBlock(tok, "ok", "{", " return \"OK\"; }",
      func(LS _tok, int nIdx) -> bool {
        //print("ok construct: " + subList(_tok, nIdx-1, nIdx+4));
        ret
          !eqGetOneOf(_tok, nIdx-1, "void", "svoid");
      });
      
    // OLD SHIZ
    //tok_identifierSemicolonAsFunctionCall(tok);
    
    // NEW SHIZ!!
    new Tok_IdentifierSemicolonToReturnStatement(tok).run();
  
    // shorter match syntax for answer methods
    
    tok_expandIfQuoted(tok);
    
    jreplace(tok, "if <id> eq <quoted>", "if (eq($2, $4))");
  
    tok_dropExtraCommas(tok);
    
    // additional translations (if necessary)
    
    jreplace(tok, "pcall ping {", "pcall { ping();");
    
    replaceKeywordBlock(tok, ") pcall",
      ") { pcall {",
      "}}");
    
    //jreplace(tok, "void <id> pcall {", "$1 $2() pcall {");
    
    tok_pcall(tok);
    
    replaceKeywordBlock(tok,
      "pcall-print",
      "try {",
      "} catch (Throwable __e) { printStackTrace(__e); }");
  
    replaceKeywordBlock(tok,
      "pcall-short",
      "try {",
      "} catch (Throwable __e) { print(exceptionToStringShort(__e)); }");
  
    replaceKeywordBlock(tok,
      "pcall-silent",
      "try {",
      "} catch (Throwable __e) { silentException(__e); }");
  
    replaceKeywordBlock(tok,
      "pcall-messagebox",
      "try {",
      "} catch __e { messageBox(__e); }");
  
    replaceKeywordBlock(tok,
      "pcall-infobox",
      "try {",
      "} catch __e { infoBox(__e); }");
  
    tok = dialogHandler(tok);
    
    replaceKeywordBlock(tok, "exceptionToUser",
      "try {",
      "} catch (Throwable __e) { ret exceptionToUser(__e); }"); 
  
    if (hasCodeTokens(tok, "twice", "{"))
      replaceKeywordBlock(tok, "twice",
        "for (int __twice = 0; __twice < 2; __twice++) {",
        "}"); 
  
    while ((i = findCodeTokens(tok, "bench", "*", "{")) >= 0) {
      int j = findEndOfBracketPart(tok, i+4)-1;
      S time = makeVar("time");
      S v = makeVar("bench");
      S n = tok.get(i+2);
      tok.set(i, "{ long " + time + " = sysNow(); for (int " + v + " = 0; " + v + " < " + n + "; " + v + "++)");
      tok.set(i+2, "");
      tok.set(j, "} printBenchResult(sysNow()-" + time + ", " + n + "); }");
      reTok(tok, i, j+1);
    }
  
    replaceKeywordBlockDyn(tok,
      "time",
      new O { S[] get() {
        S var = makeVar("startTime");
        ret new S[] {
          "{ long " + var + " = sysNow(); try { ",
          "} finally { " + var + " = sysNow()-" + var + "; saveTiming(" + var + "); } }"};
      }});
    
    // version without { }
    replaceKeywordBlockDyn(tok,
      "time2",
      new O { S[] get() {
        S var = makeVar("startTime");
        ret new S[] {
          "long " + var + " = sysNow(); ",
          " " + var + " = sysNow()-" + var + "; saveTiming(" + var + "); "};
      }});
    
    // time "bla" {
    // time msg {
    replaceKeywordPlusQuotedOrIDBlock(tok,
      "time",
      new O { S[] get(L<S> tok, int i) {
        S var = makeVar("startTime");
        ret new S[] {
          "long " + var + " = sysNow(); ",
          " done2_always(" + tok.get(i+2) + ", " + var + "); "};
      }});
    
    if (hasCodeTokens(tok, "assertFail", "{")) {
      S var = makeVar("oops");
      
      replaceKeywordBlock(tok,
        "assertFail",
        "boolean " + var + " = false; try {",
        "\n" + var + " = true; } catch (Exception e) { /* ok */ } assertFalse(" + var + ");"); 
    }
    
    replaceKeywordBlock(tok,
      "yo",
      "try {",
      "} catch (Exception " + makeVar("e") + ") { ret false; }",
      tokcondition {
        ret neqOneOf(_get(tok, i-1), "svoid", "void");
      });
  
    replaceKeywordBlock(tok,
      "awtIfNecessary",
      "swingNowOrLater(r " + "{",
      "});");
      
    ctex(tok);
      
    replaceKeywordBlock(tok,
      "actionListener",
      "new java.awt.event.ActionListener() { " +
        "public void actionPerformed(java.awt.event.ActionEvent _evt) { pcall-messagebox {",
      "}}}");
      
    for (S keyword : ll("autocloseable", "autoCloseable"))
      /*replaceKeywordBlock(tok,
        keyword,
        "new AutoCloseable() { public void close() throws Exception {",
        "}}");*/
        replaceKeywordBlock_dyn2_legacy(tok, keyword, new O {
          S[] get(LS tok, int iOpening, int iClosing) {
            LS contents = subList(tok, iOpening+1, iClosing);
            ret new S[] {
              "new AutoCloseable() { toString { ret " + quote(shorten(defaultMaxQuineLength(), trimJoin(contents))) + "; } public void close() throws Exception {",
              "}}"
            };
          }
        });
      
    // try answer (string, test with nempty)
    while ((i = findCodeTokens(tok, "try", "answer")) >= 0) {
      int j = findEndOfStatement(tok, i);
      S v = makeVar();
      bool needCurly = !eqGet(tok, i-2, "{");
      tok.set(i, (needCurly ? "{" : "") + " S " + v);
      tok.set(i+2, "=");
      tok.set(j-1, "; if (!empty(" + v + ")) ret " + v + "; " + (needCurly ? "}" : ""));
      reTok(tok, i, j);
    }
  
    // try bool[ean] (try answer with Bool type)
    while ((i = findCodeTokens(tok, "try", "boolean")) >= 0) {
      int j = findEndOfStatement(tok, i);
      S v = makeVar();
      tok.set(i, "{ Bool " + v);
      tok.set(i+2, "=");
      tok.set(j-1, "; if (" + v + " != null) ret " + v + "; }");
      reTok(tok, i, j);
    }
    
    // <statement>, print "..."; => { <statement>; print("..."); }
    while ((i = jfind(tok, ", print <quoted>;")) >= 0) {
      int j = tok_findBeginningOfStatement(tok, i);
      replaceTokens_reTok(tok, i, i+4*2-1, "; print(" + tok.get(i+4) + "); }");
      tokPrepend_reTok(tok, j, "{ ");
    }
    
    // return if null <expression> => if (<expression> == null) return;
    while ((i = jfind(tok, "return if null")) >= 0) {
      int j = findEndOfStatement(tok, i);
      clearTokens(tok, i, i+2);
      tok.set(i+4, "((");
      tok.set(j-1, ") == null) ret;");
      reTok(tok, i, j);
    }
    
    // return optional (return if not null)
    while ((i = jfind_check optional(tok, "return optional <id> =")) >= 0) {
      int j = findEndOfStatement(tok, i);
      S v = tok.get(i+4);
      clearTokens(tok, i+2, i+4);
      tok.set(i, "{");
      tok.set(j-1, "; if (" + v + " != null) ret " + v + "; }");
      reTok(tok, i, j);
    }
    
    // try object (return if not null)
    
    jreplace_dyn(tok, "try object (<id>)", (_tok, cIdx) -> {
      S type = _tok.get(cIdx+6);
      ret "try object " + type + " " + makeVar() + " = (" + type + ")";
    });

    // try object (return if not null) - now with auto-type    
    while ((i = jfind_check object(tok, "try object")) >= 0) {
      int j = findEndOfStatement(tok, i);
      clearTokens(tok, i, i+3);
      bool isDecl = isIdentifier(get(tok, i+4)) && isIdentifier(get(tok, i+6)) && eqGet(tok, i+8, "=");
      if (isDecl) {
        S v = get(tok, i+6);
        tok.set(i, "{");
        tok.set(j-1, "; if (" + v + " != null) ret " + v + "; }");
      } else {
        S v = makeVar();
        tok.set(i, "{ var " + v + "=");
        tok.set(j-1, "; if (" + v + " != null) ret " + v + "; }");
      }
      reTok(tok, i, j);
    }
    
    // try Int i = ...; (return if not null, shorter version of "try object")
    /*while ((i = jfind(tok, "try <id> <id> =")) >= 0) {
      int j = findEndOfStatement(tok, i);
      S type = tok.get(i+2), v = tok.get(i+4);
      tok.set(i, "{");
      tok.set(j-1, "; if (" + v + " != null) ret " + v + "; }");
      reTok(tok, i, j);
    }*/
    while ((i = jfind(tok, "try <id>")) >= 0) {
      int iType = i+2, iVar = tok_findEndOfType(tok, iType);
      S v = tok.get(iVar);
      assertEquals("try object", "=", get(tok, iVar+2));
      int j = findEndOfStatement(tok, iVar);
      tok.set(i, "{");
      tok.set(j-1, "; if (" + v + " != null) ret " + v + "; }");
      reTok(tok, i, j);
    }
    
    // debug print ...; => if (debug) print(...);
    while ((i = jfind(tok, "debug print")) >= 0) {
      int j = findEndOfStatement(tok, i);
      replaceTokens(tok, i, i+4, "if (debug) print(");
      tok.set(j-1, ");");
      reTok(tok, i, j);
    }
    
    functionReferences(tok);
    tok_expandLPair(tok);
    tok_expandPairL(tok);
    tok_expandLT3(tok);
    tok_quicknew2(tok);
    
    // before star constructors because tok_expandStarConstructors
    // doesn't like a meta command in front of it
    tok_delegateTo(tok);
    tok_replaceWith(tok);
    tok_replaceVarWith(tok);

    tok_exclamPostfix(tok);
    
    // before temp blocks
    tok_varNamedLikeFunction(tok);
    
    tok_onCleanExit(tok);
    
    tempBlocks(tok); // after quicknew2 for stuff like "temp new X x;"

    // X x = nu(+...)  =>  X x = nu X(+...)
    jreplace(tok, "<id> <id> = nu(+", "$1 $2 = nu $1(+");
    // X x = nu(a := ...)  =>  X x = nu X(a := ...)
    jreplace(tok, "<id> <id> = nu(<id> :=", "$1 $2 = nu $1($6 :=");
    
    tok_expandVarCopies(tok); // AFTER the lines just above
    tok_replaceColonEqualsSyntax(tok); // ditto

    tok_unpair(tok);
    tok_cachedFunctions_new(tok);
    //tok_simplyCachedFunctions(tok);
    tok_timedCachedFunctions(tok);
    
    tok_optPar(tok);
    
    throwFailEtc(tok);
    tok_typeAA(tok, pairClasses);
    tok_typeAAA(tok, tripleClasses);
    tok_typeAO(tok, litset("WithTrail"));

    // before star constructors so we can define star constructors in a macro
    tok_localMacro(tok);
    
    // do this after expanding sclass etc.
    tok = tok_expandStarConstructors(tok);
    
    tok_kiloConstants(tok);
    //tok_colonMessages(tok);
    
    while ((i = jfind(tok, "shit:")) >= 0) {
      int j = tok_findEndOfStatement(tok, i);
      tok.set(i+2, "(");
      tok.set(j-1, ");");
      reTok(tok, i, j);
    }
      
    jreplace("shit(", "ret with print(");
    
    tok_virtualTypes(tok);
    tok_autoLongConstants(tok);
    
    // common misordering of type arguments
    jreplace("boolean <A>", "<A> boolean");
    
    tok_unimplementedMethods(tok);
    tok_switchableFields(tok);
    tok_autoDisposeFields(tok);
    tok_shortVisualize(tok);
    tok_whileGreaterThan(tok);
    tok_ifThenEnd(tok);
    
    tok_autoInitVars(tok);
    
    tok_fixBadTypeParameterOrder(tok);
    
    // shortened method declarations BEFORE standardFunctions
    tok_svoidEtc(tok);
    jreplace(tok, "void <id> {", "$1 $2() {");
    jreplace(tok, "void <id> thread {", "$1 $2() thread {");
    jreplace(tok, "String <id> {", "$1 $2() {");
    jreplace(tok, "Object <id> {", "$1 $2() {");
    jreplace(tok, "List <id> {", "$1 $2() {");

    namedThreads(tok);
    threads(tok);
    
    //tok_maxEquals(tok);
    
    tok_questionDot(tok);
    
    jreplace(tok, "if (<id>?!)", "if ($3 != null && $3!)");
    
    tok_embeddedFunctions(tok);
    
    tok_quickNewArray(tok);
    jreplace("<id>[] <id> = new {", "$1[] $4 = {");

    jreplace("<id> ifNull =", "if ($1 == null) $1 =");
    
    jreplace("class <id> extends <id><.<id>>", "class $2 extends $4<$2.$7>");
    
    tok_once(tok); // must come before next line so you can combine them
    tok_ifRecordMatch(tok);
    
    jreplace(tok, "<id> ||=", "$1 = $1 ||");
    
    // magicValue followed by a numerical constant
    jreplace("magicValue", "", (_tok, _i) -> {
      S t = _get(_tok, _i+3);
      ret eqOneOf(t, ".", "-") || isInteger(t);
    });
    
    lambdaReferences(tok);
    
    tok_returnSelf(tok);
    
    // Lua-like print statement
    jreplace(tok, "print <quoted>", "print($2);");
    
    tok_tildeCalls(tok);
    
    tok_svoidEtc(tok);
    tok_swappableFunctions(tok);
    
    tok_optParLambda(tok);
    
    tok_runnableClasses(tok);
    
    tok_swapStatement(tok);
    
    //defineMapLikesEtc(tok);
    
    tok_optionalArguments(tok);
    
    tok_usualDefaults(tok);
    
    tok_defaultArguments_debug = isDef("tok_defaultArguments_debug"); 
    tok_defaultArguments(tok);
    
    tok_akaFunctionNames(tok);
    
    tok_simplyCachedFunctions(tok);
    
    tok_persistableClasses(tok);
    
    tok_transientClasses(tok);
    
    tok_shortMethodReferences(tok);
    
    jreplace(tok, "== null ?:", "== null ? null :");
    jreplace(tok, "?:", "== null ? null :");
    
    tok_orCase(tok);
    
    tok_beforeMethods(tok);
    tok_afterMethods(tok);
    
    tok_returnAsFunctionName(tok);
    
    tok_transpileGetSet(tok);
    
    tok_pcallPrefix(tok);
    
    tok_numberFunctionNames(tok);
    
    tok_castToStatements(tok);
    
    tok_optionalFields(tok);
    
    tok_getFromMap(tok);
    
    jreplace(tok, "for <id> : <id> {", "for (var $2 : $4) {");
    
    tok_shortLambdas(tok);
    
    if (metaCodeAllowed()) runTransformers(tok, localTransformers);
    
    tok_andVarMixIn(tok);
    
    tok_stages(tok);
    
    tok_beginPeriod(tok);
    
    tok_enterStatement(tok);
    
    tok_settableFields(tok);
    
    tok_reImmutableVars(tok);
    
    tok_scaffoldedFunctions(tok);
    
    while ((i = jfind(tok, "scaffoldPrint(")) >= 0) {
      tokReplace_reTok(tok, i, i+4,
        "if (scaffoldingEnabled(this)) scaffoldCalled(this, ");
      tok_statementToBlock(tok, i);
    }
    
    jreplace(tok, "<id> from method;", "var $1 = $1();");
    
    tok_whileCast(tok);
    
    tok_multiTypeArguments_v2(tok);
    
    tok_printIfdef(tok);
    
    // Doing this later than voidfunc, quicknew etc
    // because it relies on detecting anonymous classes
    tok_swingBlocks(tok);
    
    tok_defEquals(tok);
    
    tok_swapFunctions(tok);
    
    tok_dotPlus(tok);
      
    // end of local stuff
    
    tok_processMetaBlocks(tok, metaCodeAllowed());
    if (metaCodeAllowed()) runTransformers(tok, metaTransformers);

    same = eq(tok, before);
    /*if (!same)
      print("local not same " + safety + " (" + l(tok) + " tokens)");*/
    if (safety++ >= 10) {
      printSources(tok);
      fail("safety 10 error!");
    }
  } while (!same);
  
  ret tok;
}

static L<S> reTok_include(L<S> tok, int i, int j) {
  ret reTok_modify localStuff1(tok, i, j);
}

static L<S> includeInMainLoaded_reTok(L<S> tok, int i, int j) {
  ret reTok_include(tok, i, j);
}

static L<S> stdstuff(L<S> tok) {
  //if (++level >= 10) fail("woot? 10");
  
  print("stdstuff!");
  int i;
  
  new L<S> ts;
  tok_findTranslators(tok, ts);
  if (nempty(ts))
    print("DROPPING TRANSLATORS: " + structure(ts));

  print('quickmain); tok = quickmain(tok);
  print('includes); tok = tok_processIncludes(tok);
  print('conceptsDot); if (processConceptsDot(tok))
  tok = tok_processIncludes(tok);
  
  LS dontImports = tok_processDontImports(tok, definitions);
  for (S s : dontImports)
    doNotIncludeFunction.remove(afterLastDot(s));
  
  //print('starConstructors); tok = tok_expandStarConstructors(tok);
    
  // drop Java 8 annotations since we're compiling for Java 7
  jreplace(tok, "@Nullable", "");

  // STANDARD CLASSES & INTERFACES
  
  print("standard classes");
  haveClasses = addStandardClasses_v2(tok);
  
  tok_quickInstanceOf(tok, haveClasses);

  // concept-related stuff
  
  // auto-import concepts
  /*bool _a = tok_hasClassRef2(tok, "Concept") || tok_hasClassRef2(tok, "Concepts"), _b = !haveClasses.contains("Concept");
  //print("auto-import: " + _a + ", " + _b);
  if (_a && _b) {
    print("Auto-including concepts.");
    if (shouldNotIncludeClass.contains("Concepts")) {
      print(join(tok));
      fail("Unwanted concepts import");
    }
    printStruct(haveClasses);
    tok = includeInMainLoaded(tok, "concepts.");
    reTok(tok, l(tok)-1, l(tok));
    //processConceptsDot(tok);
  }*/
  
  ret tok;
} // end of stdStuff!

static L<S> multilineStrings(L<S> tok) {
  for (int i = 1; i < tok.size(); i += 2) {
    S t = tok.get(i);
    if (isQuoted(t))
      if (t.startsWith("[") || t.contains("\r") || t.contains("\n"))
        tok.set(i, quote(unquote_relaxedMLS(t)));
  }
  ret tok;
}

static L<S> quickmain(L<S> tok) {
  if (quickmainDone1 && quickmainDone2) ret tok;

  int i = findCodeTokens(tok, "main", "{");
  if (i < 0) i = findCodeTokens(tok, "m", "{");
  if (i >= 0 && !(i-2 > 0 && tok.get(i-2).equals("class"))) {
    tokSet_reTok(tok, i, (definitions.contains("mainClassPublic") ? "public " : "") + "class main");
    quickmainDone1 = true;
  }
    
  i = findCodeTokens(tok, "psvm", "{");
  if (i < 0) i = findCodeTokens(tok, "p", "{");
  if (i >= 0) {
    int idx = i+2;
    int j = findEndOfBracketPart(tok, idx)-1;
    L<S> contents = subList(tok, idx+1, j);
    //print("contents: " + sfu(contents));
    tok.set(i, "public static void main(final String[] args) throws Exception");
    replaceTokens(tok, idx+1, j, tok_addSemicolon(contents));
    reTok(tok, i, j);
    quickmainDone2 = true;
  }
    
  ret tok;
}

sS makeVar(S name) {
  AtomicInteger counter = varCountByThread!;
  if (counter == null)
    varCountByThread.set(counter = new AtomicInteger);
  ret "_" + name + "_" + getAndInc(counter);
}

static S makeVar() { ret makeVar(""); }

static L<S> rtq(L<S> tok, S id) {
  ret runTranslatorQuick(tok, id);
}

static L<S> expandShortTypes(L<S> tok) {
  // replace <int> with <Integer>
  for (int i = 1; i+4 < tok.size(); i += 2)
    if (tok.get(i).equals("<")
      && litlist(">", ",").contains(tok.get(i+4))) {
      String type = tok.get(i+2);
      if (type.equals("int")) type = "Integer";
      else if (type.equals("long")) type = "Long";
      tok.set(i+2, type);
    }
    
  for (key, val : javaxClassShortcuts())
    jreplace(tok, key, val);

  var tcShortPrimitive = tokCondition {
    ret neqGetOneOf(tok, i+3, "(", null);
  };
  
  // bool -> boolean if it's not a function name
  jreplace(tok, "bool", "boolean", tcShortPrimitive);
  
  //      dbl x;     => double x;
  // BUT: void dbl() => dbl()

  jreplace(tok, "dbl", "double", tcShortPrimitive);
  jreplace(tok, "Dbl", "Double", tcShortPrimitive);
  
  jreplace(tok, "AtomicBool", "AtomicBoolean");
  jreplace(tok, "AtomicInt", "AtomicInteger");

  tok_selfNestedType(tok, "LL", "L", true);
  tok_selfNestedType(tok, "MatrixOfMatrices", "Matrix", false);
  jreplace(tok, "LPt", "L<Pt>");
  
  jreplace(tok, "Clusters< <id> >", "Map<$3, Collection<$3>>");
  
  ret tok;
}

static L<S> autoImports(L<S> tok) {
  HashSet<S> imports = new HashSet(tok_findImports(tok));
  new StringBuilder buf;
  for (S c : standardImports())
    if (!(imports.contains(c)))
      buf.append("import " + c + ";\n");
  if (buf.length() == 0) ret tok;
  tok.set(0, buf+tok.get(0));
  ret reTok(tok, 0, 1);
}

static L<S> tok_processIncludes(L<S> tok) {
  int safety = 0;
  while (hasCodeTokens(tok, "!", "include") && ++safety < 100)
    tok = tok_processIncludesSingle(tok);
  
  //tok_autoCloseBrackets(tok);
  ret tok;
}

svoid tok_processEarlyIncludes(L<S> tok) {
  int i;
  while ((i = jfind_check include(tok, "!include early #<int>")) >= 0) {
    S id = tok.get(i+8);
    included.add(parseLong(id));
    replaceTokens_reTok(tok, i, i+10, "\n" + cacheGet(id) + "\n");
  }
  
  // !include string (include as string constant)
  // doing this early because it didn't work in imports otherwise
  
  while ((i = jfind_check include(tok, "!include string #<int>")) >= 0) {
    S id = tok.get(i+8);
    included.add(parseLong(id));
    replaceTokens_reTok(tok, i, i+10, quote(cacheGet(id)));
  }
}

static L<S> tok_processIncludesSingle(L<S> tok) {
  // simple !include
  
  int i;
  while ((i = jfind_check include(tok, "!include #<int>")) >= 0) {
    S id = tok.get(i+6);
    included.add(parseLong(id));
    replaceTokens(tok, i, i+8, "\n" + cacheGet(id) + "\n");
    reTok_include(tok, i, i+8);
  }
  
  // !include once
  
  while ((i = jfind_check include(tok, "!include once #<int>")) >= 0) {
    S id = tok.get(i+8);
    bool isNew = included.add(parseLong(id));
    replaceTokens(tok, i, i+10, 
      isNew ? "\n" + cacheGet(id) + "\n" : "");
    reTok_include(tok, i, i+10);
  }
  
  ret tok;
}

// ctex and various other error-related keyword blocks
static void ctex(L<S> tok) {
  replaceKeywordBlock(tok, "ctex",
    "{ try {",
    "} catch (Exception __e) { throw rethrow(__e); } }");
  for (S keyword : ll("null on exception", "null on error"))
    replaceKeywordBlock(tok, keyword,
      "{ try {",
      "} catch (Throwable __e) { return null; } }");
  replaceKeywordBlock(tok, "false on exception",
    "{ try {",
    "} catch (Throwable __e) { return false; } }");
  replaceKeywordBlock(tok, "try-OrError",
    "{ try {",
    "} catch (Throwable __e) { return OrError.error(__e); } }");
}
  
static L<S> dialogHandler(L<S> tok) {
  ret replaceKeywordBlock(tok,
    "dialogHandler",
    "new DialogHandler() {\n" +
      "public void run(final DialogIO io) {",
    "}}");
}

static L<S> extendClasses(L<S> tok) {
  int i;
  while ((i = jfind(tok, "extend <id> {")) >= 0) {
    S className = tok.get(i+2);
    int idx = findCodeTokens(tok, i, false, "{");
    int j = findEndOfBracketPart(tok, idx+2);
    S content = joinSubList(tok, idx+1, j-1);
    L<S> c = findInnerClassOfMain(tok, className);
    print("Extending class " + className);
    clearTokens(subList(tok, i, j+1));
    if (c == null) {
      print("Warning: Can't extend class " + className + ", not found");
      continue;
    }
    int startOfClass = indexOfSubList(tok, c);
    int endOfClass = startOfClass + l(c)-1;
    //print("Extending class " + className + " ==> " + join(subList(tok, startOfClass, endOfClass)));
    while (neq(tok.get(endOfClass), "}")) --endOfClass;
    //print("Extending class " + className + " ==> " + join(subList(tok, startOfClass, endOfClass)));
    tok.set(endOfClass, content + "\n" + tok.get(endOfClass));
    
    doubleReTok(tok, i, j+1, endOfClass, endOfClass+1);
  }
  ret tok;
}

// for ping / while ping
static void forPing(L<S> tok) {
  int i;
  for (S keyword : ll("for", "fOr", "while"))
    while ((i = jfind(tok, keyword + " ping (")) >= 0) {
      int bracketEnd = findEndOfBracketPart(tok, i+4)-1;
      int iStatement = bracketEnd+2;
      int iEnd = findEndOfStatement(tok, iStatement);
      tok.set(i+2, "");
      
      // turn into block
      if (!eq(get(tok, iStatement), "{")) {
        tok.set(iStatement, "{ " + tok.get(iStatement));
        tok.set(iEnd-1, tok.get(iEnd-1) + " }");
      }
        
      // add ping
      tok.set(iStatement, "{ ping(); " + dropPrefixTrim("{", tok.get(iStatement)));
      reTok(tok, i+2, iEnd);
    }
}

// lib 123 => !123
static void libs(L<S> tok) {
  int i;
  while ((i = jfind(tok, "lib <int>")) >= 0) {
    S id = tok.get(i+2);
    print("lib " + id);
    if (!libs.contains(id)) {
      libs.add(id);
      clearAllTokens(tok, i, i+3);
      /*tok.set(i, "!");
      tok.set(i+1, "");*/
    } else {
      print("...ignoring (duplicate)");
      clearAllTokens(tok, i, i+3);
      reTok(tok, i, i+3);
    }
  }
  print("libs found: " + libs);
}

// sourceCodeLine() => 1234
static void sourceCodeLine(L<S> tok) {
  int i ;
  while ((i = jfind(tok, "sourceCodeLine()")) >= 0) {
    replaceTokens(tok, i, i+5, str(countChar(joinSubList(tok, 0, i), '\n')+1));
    reTok(tok, i, i+5);
  }
}

// done before any other processing
svoid earlyStuff(LS tok) {
  int i;
  
  tok_processEarlyIncludes(tok);
      
  tok_scopes(tok, autoCloseScopes := asInclude);
  tok_autosemi(tok);
  tok_autoCloseBrackets(tok);
  jreplace(tok, "°", "()");
  
  // Note: this makes the word "quine" a special operator
  // (unusable as a function name)
  
  while ((i = jfind(tok, "quine(")) >= 0) {
    int idx = findCodeTokens(tok, i, false, "(");
    int j = findEndOfBracketPart(tok, idx+2);
    tok.set(i, "new Quine");
    tok.set(idx, "(" + quote(joinSubList(tok, idx+1, j-1)) + ", ");
    reTok(tok, i, idx+1);
  }
  
  jreplace_check after(tok, "void <id> after super {", "void $2 { super.$2();");
  
  replaceKeywordBlock(tok, "r-enter", "r { enter {", "}}");
    
  // do this before func & voidfunc because otherwise they swallow it
  jreplace(tok, "enter {", "{ temp enter();");
  
  tok_mutatorMethods(tok);
  
  // func keyword for lambdas - now automatically quines toString() if enabled
  
  replaceKeywordBlock(tok,
    "null",
    "{",
    "null; }");
    
  // do func & voidfunc early to preserve original code as toString
  
  while ((i = jfind(tok, "func(")) >= 0) {
    int argsFrom = i+4, argsTo = findCodeTokens(tok, i, false, ")");
    int idx = findCodeTokens(tok, argsTo, false, "{");
    int j = findEndOfBracketPart(tok, idx);
    L<S> contents = subList(tok, idx+1, j-1);
    
    S returnType = "O";
    if (eq(tok.get(argsTo+2), "-") && eq(tok.get(argsTo+4), ">"))
      returnType = tok_toNonPrimitiveTypes(joinSubList(tok, argsTo+6, idx-1));
      
    S toString = autoQuine ? "  public S toString() { ret " + quote(shorten(defaultMaxQuineLength(), trimJoin(contents))) + "; }" : "";
    
    L<S> args = cloneSubList(tok, argsFrom-1, argsTo);
    tok_shortFinals(args);
    tok_toNonPrimitiveTypes(args);
    
    L<S> types = tok_typesOfParams(args);
    O type = "O";
    if (l(types) <= 3)
      type = "F" + l(types) + "<" + joinWithComma(types) + ", " + returnType + ">";
    S body = tok_addReturn(contents);
    
    replaceTokens_reTok(tok, i, j,
      "new " + type + "() { public "
        + returnType + " get(" + trimJoin(args) + ") ctex { "
          + body
        + " }\n" +
       + toString + "}");
  }
  
  while ((i = jfind(tok, "voidfunc(")) >= 0) {
    int argsFrom = i+4, argsTo = findCodeTokens(tok, i, false, ")");
    int idx = findCodeTokens(tok, argsTo, false, "{");
    int j = findEndOfBracketPart(tok, idx);
    L<S> contents = subList(tok, idx+1, j-1);
    
    if (jcontains(subList(tok, argsTo+1, idx), "->"))
      fail("voidfunc with return type: " + joinSubList(tok, i, j+1));
    
    L<S> args = cloneSubList(tok, argsFrom-1, argsTo);
    tok_shortFinals(args);
    tok_toNonPrimitiveTypes(args);
    
    L<S> types = tok_typesOfParams(args);
    O type = "O";
    if (l(types) <= 4)
      type = "VF" + l(types) + "<" + joinWithComma(types) + ">";

    replaceTokens(tok, i, j, "new " + type + "() { public void get(" + trimJoin(args) + ") ctex { " + tok_addSemicolon(contents) + " }\n" +
    (autoQuine ? "  public S toString() { ret " + quote(shorten(defaultMaxQuineLength(), trim(join(contents)))) + "; }" : "") + "}");
    reTok(tok, i, j);
  }
  
  jreplace(tok, "func {", "func -> O {");
  jreplace(tok, "f {", "f -> O {");
  
  // swing -> S { ... } => swing(func -> S { ... })
  while ((i = jfind(tok, "swing ->")) >= 0) {
    int bracket = findCodeTokens(tok, i, false, "{");
    int j = findEndOfBracketPart(tok, bracket);
    tok.set(i, "swing(func");
    tok.set(j-1, "})");
    reTok(tok, i, j);
  }
  
  tok_qFunctions(tok);
  
  jreplace(tok, "func fullToString {", "func -> O fullToString {");
  
  for (S keyword : ll(/*"f",*/ "func")) {
    while ((i = jfind(tok, keyword + " ->", tokcondition {
      ret isIdentifier(_get(tok, i+7)); // avoid lambda declaration like: f -> { ... }
    })) >= 0) {
      // I think there is a bug here for something like func -> x { new x { } }
      int idx = findCodeTokens(tok, i, false, "{");
      int j = findEndOfBracketPart(tok, idx);
      S returnType = tok_toNonPrimitiveTypes(joinSubList(tok, i+6, idx-1));
      int quineLength = defaultMaxQuineLength();
      if (eq(lastJavaToken(returnType), "fullToString")) {
        quineLength = Int.MAX_VALUE;
        returnType = dropLastJavaTokenAndSpacing(returnType);
      }
      L<S> contents = subList(tok, idx+1, j-1);
      replaceTokens(tok, i, j, "new F0<" + returnType + ">() { public " + returnType + " get() ctex { " + tok_addReturn(contents) + " }\n" +
        (autoQuine ? "  public S toString() { ret " + quote(shorten(quineLength, trimJoin(contents))) + "; }" : "") + "}");
      reTok(tok, i, j);
    }
  }
    
  while ((i = jfind(tok, "time repeat * {")) >= 0) {
    int j = findEndOfBlock(tok, i+6)-1;
    tok.set(i, "time {");
    tok.set(j, "}}");
    reTok(tok, i, j+1);
  }

  // do this before "m {" stuff because "repeat m" [doesn't seem to work yet though)
  while ((i = findCodeTokens(tok, "repeat", "*", "{")) >= 0) {
    S v = makeVar("repeat");
    tok.set(i, "for (int " + v + " = 0; " + v + " < " + tok.get(i+2) + "; " + v + "++)");
    tok.set(i+2, "");
    reTok(tok, i, i+3);
  }
}

// fail(); => throw fail();
// unimplemented(); => throw unimplemented();
// etc
static void throwFailEtc(L<S> tok) {
  bool anyChange = false;
  for (int i = 1; i+4 < l(tok); i += 2)
    if (eqOneOf(get(tok, i+2), "fail", "todo", "unimplemented")
      && eq(get(tok, i+4), "(")
      && !eqOneOf(get(tok, i), "throw", "RuntimeException", "return", "f", "function", ".", "void", "main", "Throwable")) {
      tok.set(i+2, "throw " + tok.get(i+2));
      anyChange = true;
    }
  if (anyChange)
    reTok(tok);
}

static void namedThreads(L<S> tok) {
  for (int i = 0; i < 100; i++) {
    int idx = findCodeTokens(tok, "thread", "<quoted>", "{");
    if (idx < 0) idx = findCodeTokens(tok, "thread", "<id>", "{");
    if (idx < 0)
      break;
    int j = findEndOfBracketPart(tok, idx+4);
    S tName = tok.get(idx+2);
    
    S pre = "startThread(" + tName + ", r { ";
    S post = "})";
    if (!tok_tokenLeftOfExpression(tok, idx-2)) post += ";";

    tok.set(idx, pre);
    tok.set(idx+2, "");
    tok.set(idx+4, "");
    tok.set(j-1, post);
    //print(join(subList(tok, idx, j)));
    reTok(tok, idx, j);
  }
}

static void rNamedThread(L<S> tok) {
  for (int i = 0; i < 100; i++) {
    int idx = findCodeTokens(tok, "r", "-", "thread", "<quoted>", "{");
    if (idx < 0) idx = findCodeTokens(tok, "r", "-", "thread", "<id>", "{");
    if (idx < 0)
      break;
    int j = findEndOfBracketPart(tok, idx+8);
    S tName = tok.get(idx+6);
    
    S pre = "r { thread " + tName + " {";
    S post = "}}";

    replaceTokens(tok, idx, idx+9, pre);
    tok.set(j-1, post);
    reTok(tok, idx, j);
  }
}

static void threads(L<S> tok) {
  replaceKeywordBlock(tok, "daemon", "startDaemonThread(r {", "});");
  //replaceKeywordBlock(tok, "thread", "startThread(r {", "});");
  
  // now enclose in { } to allow using like "void bla() thread { ... }" - if it's not used as an expression
  
  replaceKeywordBlock_dyn2_legacy(tok, "thread", new O { // don't use func here, it can't be transpiled
    S[] get (LS tok, int iOpening, int iClosing) {
      // is the thread clause used as an expression?
      bool isExpression = tok_tokenLeftOfExpression(tok, iOpening-4);
      ret new S[] {
        (isExpression ? "" : "{ ") + "startThread(r {",
        "})" +
        (isExpression ? "" : "; }")
      };
    }
  });
}

static SS sf; // standard standard functions (haha)
static Bool _761ok;

static LS standardFunctions(LS tok) {
  if (sf == null) {
    S _761 = cacheGet("#761");
    if (_761ok == null)
      _761ok = isBracketHygienic(_761);
    assertTrue("Whoa! #761 truncated?", _761ok);
    L<S> standardFunctions = concatLists(
      (L) loadVariableDefinition(_761, "standardFunctions"),
      (L) loadVariableDefinition(cacheGet("#1006654"), "standardFunctions"));

    sf = new HashMap;
    for (S x : standardFunctions) {
      S[] f = x.split("/");
      sf.put(f[1], f[0]);
    }
  }
  
  SS sfMap = combinedMap(extraStandardFunctions, sf);
    
  for (int i = 0; ; i++) {
    print("Looking for required functions");
    Set<S> defd = new HashSet(findFunctions(tok));
    
    int j;
    while ((j = jfind(tok, "should not include function *.")) >= 0) {
      S fname = tok.get(j+8);
      shouldNotIncludeFunction.add(fname);
      clearAllTokens(subList(tok, j, j+12));
    }

    while ((j = jfind(tok, "do not include function *.")) >= 0) {
      S fname = tok.get(j+8);
      doNotIncludeFunction.add(fname);
      clearAllTokens(subList(tok, j, j+12));
    }
    
    while ((j = jfind(tok, "need latest")) >= 0) {
      int k = j+4;
      while (!eqGetOneOf(tok, k, ".", null)) {
        S t = tok.get(k);
        if (isIdentifier(t)) {
          needLatest.add(t);
          doNotIncludeClass.remove(t);
        }
        k += 2;
      }
      clearTokens_reTok(tok, j, k+2);
    }
    
    grabImportedStaticFunctions(tok);
    doNotIncludeFunction.removeAll(needLatest);
    
    // changes tok
    //Set<String> invocations = findFunctionInvocations(tok, sfMap, hardFunctionReferences, defd, true, mainClassName());
    Set<String> invocations = findFunctionInvocations_v2(tok, sfMap, hardFunctionReferences, defd, true, mainClassName(), containsKeyPredicate(standardClassesMap()));
    
    /*if (invocations.contains("str"))
      print("==STR==" + join(tok) + "==STR==");*/
    if (!cic(definitions, "leanMode"))
      invocations.addAll(functionsToAlwaysInclude);

    //print("Functions invoked: " + structure(invocations));
    Set<S> needed = setMinusSet(invocations, defd);
    for (S f : doNotIncludeFunction) needed.remove(f);
    if (needed.isEmpty())
      break;
    print("Adding functions: " + join(" " , needed));
    
    Cl<S> bad = setIntersection(needed, shouldNotIncludeFunction);
    if (nempty(bad)) {
      S msg = "INCLUDING BAD FUNCTIONS: " + sfu(bad);
      print(msg);
      print(join(tok));
      fail(msg);
    }
      
    new LS added;
    new L<Future<S>> parts;
    new LS preload;
    
    for (S x : needed)
      if (sfMap.containsKey(x))
        preload.add(sfMap.get(x));
    print("Preloading: " + preload);
    cachePreload(preload);
    
    for (String x : cloneList(needed)) {
      if (defd.contains(x)) continue;
      
      String id = sfMap.get(x);
      if (id == null) {
        print("Standard function " + x + " not found.");
        needed.remove(x);
        continue;
      }
      //print("Adding function: " + x + " (" + id + ")");
       
      S function = cacheGet(id) + "\n";
      //if (("\n" + function).contains("\n!")) print("Warning: " + id + " contains translators.");
      
      if (cacheStdFunctions) {
        long _id = psI(id);
        CachedInclude ci = cachedIncludes.get(_id);
        if (ci == null) {
          cachedIncludes.put(_id, ci = new CachedInclude(_id));
          //println("Caching include " + _id + ", l=" + l(cachedIncludes));
        }
        function += "\n";
        fS _function = function;
        if (neq(ci.javax, function)) {
          print("Compiling function: " + x);
          ci.javax = function;
          ci.java = executor.submit(new Callable<S>() {
            public S call() {
              // We assume that variables made with makeVar() will always be local to some block
              varCountByThread.set(null);
              ret join(localStuff1(jtok(_function)));
            }
          });
          ci.realJava = null;
        }
        parts.add(ci.javaFuture());
      } else
        parts.add(nowFuture(function));
        
      added.add(x);
      Collection<S> newFunctions = new HashSet(findFunctionDefsAtCurlyLevel(0, javaTok(function)));
      defd.addAll(newFunctions);
      for (S f : newFunctions)
        if (!addedFunctions.add(f)) {
          printSources(tok);
          fail("Trying to add function " + f + " again - main class syntax broken!");
        }
    }
    
    print("Getting " + nParts(parts));
    S text = lines(getAllFutures(parts));
    print("Including " + nParts(parts));
    tok = includeInMainLoaded(tok, text);
      
    // defd = new HashSet(findFunctions(tok));
    //print("Functions added: " + joinWithSpace(added));
    
    for (String x : needed)
      if (!defd.contains(x)) {
        print(join(tok));
        fail("Function not defined properly: " + x);
      }
    //print("Iteration " + (i+2));
    
    print("Processing definitions");
    
    dontPrint('definitions); tok_definitions(tok);
    dontPrint('ifndef); tok_ifndef(tok);
    dontPrint('ifdef); tok_ifdef(tok, l1 isDefined);
    
    if (i >= 1000) fail("Too many iterations");
  }
  
  ret tok;
}

static LS findFunctions(LS tok) {
  ret findFunctionDefsAtCurlyLevel(1, findMainClass(tok));
}

sS cacheGet(S snippetID) {
  snippetID = formatSnippetID(snippetID);
  cacheRequested.add(snippetID);
  S text = snippetCache.get(snippetID);
  if (text == null) {
    text = loadSnippet(snippetID);
    // very early processing/checks for includes
    
    if (hasUnclosedStringLiterals(text))
      fail("Unclosed string literals in " + snippetID);
      
    if (regexpContains("\\bscope\\b", text)) {
      LS tok = javaTok(text);
      tok_scopes(tok, autoCloseScopes := true);
      text = join(tok);
    }
    
    snippetCache.put(snippetID, text);
  }
  ret text;
}

svoid cachePreload(Cl<S> ids) {
  new LS needed;
  fOr (S id : ids)
    if (!snippetCache.containsKey(formatSnippetID(id)))
      needed.add(formatSnippetID(id));
  if (l(needed) > 1) {
    L<S> texts = loadSnippets(needed);
    for (int i = 0; i < l(needed); i++)
      if (texts.get(i) != null)
        snippetCache.put(needed.get(i), texts.get(i));
  }
}

static L<S> jtok(L<S> tok) {
  ret jtok(join(tok));
}

static L<S> jtok(S s) {
  ret indexTokenList(javaTok(s));
}

static HashSet<S> haveClasses_actual(L<S> tok) {
  new HashSet<S> have;
  for (L<S> c : innerClassesOfMain(tok))
    have.add(getClassDeclarationName(c));
  ret have;
}

static HashSet<S> haveClasses_addImported(LS tok, HashSet<S> have, bool mainLevel default true) {
  have.addAll(setMinusSet(
    tok_importedClassNames(tok, mainLevel ? lambda2 onImportFound : null),
    needLatest));
  have.addAll(usualJavaClassNames()); // for S => S.class
  ret have;
}

static SS standardClassesMap() {
  if (standardClassesMap == null) {
    standardClassesMap = new Map;
    for (S snippetID : standardClassesSnippetIDs()) {
      S sc = cacheGet(snippetID);
      for (S line : tlft_j(sc)) {
        int idx = line.indexOf('/');
        standardClassesMap.put(line.substring(0, idx), fsI(line.substring(idx+1)));
      }
    }
  }
  ret standardClassesMap;
}

// works on Java level (no "sclass" etc)
// returns list of classes we have (useful for other processing)
static HashSet<S> addStandardClasses_v2(L<S> tok) {

  for (int safety = 0; safety < 10; safety++) {
    HashSet<S> have = haveClasses_actual(tok);
    haveClasses_addImported(tok, have);
    have.addAll(keys(rewrites));

    int j;
    while ((j = jfind(tok, "should not include class *.")) >= 0) {
      S cname = tok.get(j+8);
      shouldNotIncludeClass.add(cname);
      clearAllTokens(subList(tok, j, j+12));
    }
    
    while ((j = jfind(tok, "do not include class *.")) >= 0) {
      S name = tok.get(j+8);
      if (!needLatest.contains(name)) doNotIncludeClass.add(name);
      clearAllTokens(subList(tok, j, j+12));
    }
    
    new SS need;
    new Set<S> snippets;
    Set<S> idx = tokenIndexWithoutIfclass_forStdClasses(tok);
    
    while ((j = jfind(tok, "please include class *.")) >= 0) {
      S cname = tok.get(j+6);
      print("Found: please include class " + cname);
      idx.add(cname);
      clearAllTokens(subList(tok, j, j+10));
    }

    for (className, snippetID : standardClassesMap()) {
      if (idx.contains(className) && !have.contains(className) && snippets.add(snippetID))
        need.put(className, snippetID);
    }
    
    if (hasDef("SymbolAsString")) {
      print("Have SymbolAsString.");
      if (need.containsKey("Symbol")) {
        print("Have Symbol.");
        need.remove("Symbol");
      }
    } else
      print("No SymbolAsString.");
      
    removeAll(need, doNotIncludeClass);
    if (empty(need)) ret have;
  
    for (S className : keys(need))
      if (shouldNotIncludeClass.contains(className)) {
        S msg = "INCLUDING BAD CLASS: " + className;
        print(msg);
        print(join(tok));
        fail(msg);
      }
      
    cachePreload(values(need));
    
    new LPair<S, CachedInclude> parts; // class name, Java code
    
    print("Adding classes: " + joinWithSpace(keys(need)));
    for (S className : keys(need)) {
      if (have.contains(className)) continue; // intermittent add
      S snippetID = need.get(className);
      snippetID = fsI(snippetID);
      S text = cacheGet(snippetID);
      print("Added class " + className + " / " + snippetID + ", md5: " + md5(text));
      text += "\n";
      reMutable text;
      
      assertTrue(cacheStdClasses);
      long _id = psI(snippetID);
      
      // mark as included (the continue should never happen)
      if (!included.add(_id)) continue;
      
      CachedInclude ci = cachedIncludes.get(_id);
      if (ci == null) cachedIncludes.put(_id, ci = new CachedInclude(_id));
      if (neq(ci.javax, text)) {
        print("Compiling class: " + className);
        ci.javax = text;
        ci.java = executor.submit(new Callable<S>() {
          public S call() {
            // We assume that variables made with makeVar() will always be local to some block
            varCountByThread.set(null);
            ret join(localStuff1(jtok(text)));
          }
        });
        ci.realJava = null;
      }
      parts.add(pair(className, ci));
    }
    
    new StringBuilder buf;
    for (Pair<S, CachedInclude> p : parts) {
      S className = p.a;
      LS ct = javaTok(p.b.java());
      new SS rewritten;
      tok_findAndClearRewrites(ct, rewritten);
      if (rewritten.containsKey(className))
        have.add(className);
      for (LS c : allClasses(ct)) {
        S name = getClassDeclarationName(c);
        have.add(name);
      }
      
      haveClasses_addImported(ct, have, false);
      
      if (!have.contains(className))
        fail("Wrongly defined class: " + className + " / " + p.b.snippetID + "\n\n" + p.b.java());
      if (!addedClasses.add(className)) {
        printSources(tok);
        fail("Trying to add class " + className + " again - main class syntax broken!");
      }
      buf.append(p.b.java());
    } // for part
    
    tok = includeInMainLoaded(tok, str(buf));
  }
  fail("safety 10");
}

static Set<S> expandableClassNames = lithashset("BigInteger");

// no reTok - leaves tok dirty
// magically append ".class" to class name references
svoid expandClassReferences_lazy(L<S> tok, Set<S> classNames, L<IntRange> reToks default null) {
  for (int i = 3; i+2 < l(tok); i += 2) {
    S t = tok.get(i);
    
    // skip implements/extends/throws lists
    if (eqOneOf(t, "implements", "extends", "throws")) {
      i = tok_endOfImplementsList(tok, i);
      continue;
    }
    
    if (classNames.contains(t) || expandableClassNames.contains(t)) {
      S s = tok.get(i-2); t = tok.get(i+2);
      // Now s is token before class name, t is token after class name
      // TODO: This whole logic ain't very good
      // (Hard to distinguish between "Int.class" as an argument
      // and "Int" as a type parameter.)
      if (eqOneOf(s, "instanceof", "new", ".", "<", ">", "/", "nu")) continue;
      if (eq(t, ":")) continue; // e.g. String::concat
      if (isInteger(s)) continue;
      if (isIdentifier(s) && !eqOneOf(s, "ret", "return")) continue;
        
      if (eq(t, ",") && isIdentifier(get(tok, i+4)) && eqGet(tok, i+6, ">")) continue; // e.g. T3<L<S>, S, S>
      if (eq(s, ",") && isIdentifier(get(tok, i-4)) &&
        (eqGet(tok, i-6, "<") || eqGet(tok, i-6, ",")
        && isIdentifier(get(tok, i-8)) && eqGet(tok, i-10, "<"))) continue; // e.g. T3<S, S, S> or IF3<S, S, S, S>
      if (eq(s, ",") && eqOneOf(_get(tok, i-6), "implements", "throws")) continue;
      
      // check for cast
      if (eq(s, "(") && eq(t, ")") && i >= 5) {
        if (!eqOneOf(get(tok, i+4), "{", ";")) {
          S x = tok.get(i-4);
          if (!isIdentifier(x)) continue;
          if (eqOneOf(x, "ret", "return")) continue;
        }
      }
      
      // check following token
      if (eqOneOf(t, ",", ")", ";", ":", "|", "}")) {
        tok.set(i, tok.get(i) + ".class");
        reToks?.add(intRange(i, i+1));
      }
    }
  }
}

svoid expandClassReferences(L<S> tok, Set<S> classNames) {
  new L<IntRange> reToks;
  expandClassReferences_lazy(tok, classNames, reToks);
  reTok_multi(tok, reToks);
}

// "<id>/<ClassName>" => "((ClassName) <id>)"
static void slashCasts(L<S> tok, final Set<S> classNames) {
  /*jreplace(tok, "<id>/<id>", "(($3) $1)", tokcondition {
    ret classNames.contains(tok.get(i+5));
  });*/
  int n = l(tok)-4;
  for (int i = 1; i < n; i += 2)
    if (tok.get(i+2).equals("/") && isIdentifier(tok.get(i))
      && classNames.contains(tok.get(i+4)))
      replaceTokens_reTok(tok, i, i+5, "((" + tok.get(i+4) + ") " + tok.get(i) + ")");
}

// "<ClassName>(...)" => "new <ClassName>(...)"
// doesn't work at beginning of statement as we can't easily
// distinguish it from a constructor declaration.
static void newWithoutNew(L<S> tok, final Set<S> classNames) {
  TokCondition cond = newWithoutNew_condition(classNames);
  jreplace(tok, "<id>(", "new $1(", cond);
  // just two cases with type args for now
  jreplace(tok, "<id><<id>>(", "new $1<$3>(", cond);
  jreplace(tok, "<id><>(", "new $1<>(", cond);
}

static TokCondition newWithoutNew_condition(final Set<S> classNames) {
  ret tokcondition {
    if (!classNames.contains(tok.get(i+1))) false;
    S prev = _get(tok, i-1);
    bool ok = //!(eqGet(tok, i-3, "ifclass") && isIdentifier(prev))
      nempty(prev) // discarded ifclass
      && (eq(prev, ">") ? eqGet(tok, i-3, "-")
      : neqOneOf(prev, "new", ";", "}", "{", "public", "protected", "private", "."));
    //print("newWithoutNew: checking " + struct(subList(tok, i-3, i+2)) + " => " + ok);
    ret ok;
  };
}

static bool processConceptsDot(L<S> tok) {
  bool anyChange = false, change;
  do {
    change = false;
    for (int i : jfindAll(tok, "concepts."))
      if (contains(get(tok, i+3), "\n")) {
        replaceTokens(tok, i, i+3, "!" + "include once #1004863 // Dynamic Concepts");
        reTok(tok, i, i+3);
        change = anyChange = true;
        break;
      }
  } while (change);
  ret anyChange;
}

svoid caseAsVariableName(L<S> tok) {
  if (!tok.contains("case")) ret;
  for (int i = 1; i+2 < l(tok); i += 2) {
    S t = tok.get(i+2);
    if (tok.get(i).equals("case")
      && !(t.startsWith("'") || isInteger(t) || isIdentifier(t) || isQuoted(t)
        || eq(t, "-") && eqGet(tok, i+3, "") && isInteger(get(tok, i+4))))
      tok.set(i, "_case");
  }
}

static void continueAsFunctionName(L<S> tok) {
  jreplace(tok, "continue(", "_continue(");
}

// f bla => "bla" - and "please include function bla."
static void functionReferences(L<S> tok) {
  int i;
  
  if (definitions.contains("callF_legacy")) {
    jreplace_dyn(tok, "f-thread <id>", func(L<S> tok, int cIdx) {
      "dynamicCallableMC_thread(" + quote(tok.get(cIdx+6)) + ")"
    });
    
    S keyword = "f";
    while ((i = jfind(tok, keyword + " <id>", tokcondition {
      ret !eqOneOf(tok.get(i+3), "instanceof", "default");
    })) >= 0) {
      S f = tok.get(i+2);
      clearTokens(tok, i, i+2);
      tok.set(i+2, quote(f));
      reTok(tok, i, i+2);
      tok.set(l(tok)-1, last(tok) + "\nplease include function " + f + ".");
      reTok(tok, l(tok)-1, l(tok));
    }
  }
  
  // r|rThread|rEnter|rThreadEnter|rEnterThread fname => r|rThread|... { fname() }
  while ((i = jfindOneOf_cond(tok, tokcondition {
    ret !eqOneOf(tok.get(i+3), "instanceof", "aka", "default")
      && !eq(_get(tok, i-1), "cast");
  }, "r <id>", "rThread <id>", "rEnter <id>", "rThreadEnter <id>",
    "rEnterThread <id>")) >= 0) {
    S f = tok.get(i+2);
    replaceTokens(tok, i, i+3, tok.get(i) + " { " + f + "(); }");
    reTok(tok, i, i+3);
  }
  
  // dm_q fname => r_dm_q(r fname)
  jreplace(tok, "dm_q <id>", "r_dm_q(r $2)");
  
  // vf<S> fname => voidfunc(S s) { fname(s) }
  jreplace(tok, "vf<<id>> <id>", "voidfunc($3 a) { $5(a) }");
  
  // vf<L<S>> fname => voidfunc(L<S> a) { fname(a) }
  jreplace(tok, "vf<<id><<id>>> <id>", "voidfunc($3<$5> a) { $8(a) }");
  
  // construct<S> Entry => func(S s) -> Entry { new Entry(s) }
  jreplace(tok, "construct<<id>> <id>", "func($3 a) -> $5 { new $5(a) }");
  
  // f<S> fname => func -> S { fname() }
  jreplace(tok, "f<<id>> <id>", "func -> $3 { $5() }");
  
  // f<S, S> fname => func(S x) -> S { fname(x) }
  jreplace(tok, "f<<id>, <id>> <id>", "func($3 x) -> $5 { $7(x) }");
  
  // f<S, L<S>> fname => func(S x) -> L<S> { fname(x) }
  jreplace(tok, "f<<id>, <id><<id>>> <id>", "func($3 x) -> $5 $6 $7 $8 { $10(x) }");
  
  // f<L<S>, S> fname => func(L<S> x) -> S { fname(x) }
  jreplace(tok, "f<<id><<id>>, <id>> <id>", "func($3 $4 $5 $6 x) -> $8 { $10(x) }");
  
  // f<S, L<S>, S> fname => func(S x, L<S> y) -> S { fname(x, y) }
  jreplace(tok, "f<<id>, <id><<id>>, <id>> <id>", "func($3 x, $5 $6 $7 $8 y) -> $10 { $12(x, y) }");
  
  // if1 fname => a -> fname(a)
  // ivf1 fname => a -> fname(a)
  for (S _keyword : ll("if1", "ivf1"))
    jreplace_dyn(tok, _keyword + " <id>", func(LS tok, int i) -> S {
      S var = makeVar();
      ret var + " -> " + tok.get(i+2) + "(" + var + ")";
    });
}

static void quicknu(L<S> tok) {
  jreplace(tok, "nu <id>(", "nu($2.class, "); // not needed anymore
  jreplace(tok, "nu <id>", "new $2");
}

// fill variable innerClasses_list
static void innerClassesVar(L<S> tok, Set<S> have) {
  int i = jfind_check myInnerClasses_list(tok, ">myInnerClasses_list;");
  if (i < 0) ret;
  tok.set(i+4, "=litlist(\n" + joinQuoted(", ", have) + ");");
  reTok(tok, i+4, i+5);
}

// fill variable innerClasses_list
static void fillVar_transpilationDate(L<S> tok) {
  int i = jfind_check myTranspilationDate_value(tok, "long myTranspilationDate_value;");
  if (i < 0) ret;
  tok.set(i+4, " = " + now() + "L;");
  reTok(tok, i+4, i+5);
}

sbool ifclass_reTokImmediately = false;
sbool ifclass_noReTok = true;

// process ifclass x ... endif blocks
static void tok_ifclass(LS tok, Set<S> have) {
  tok_conditionals(tok, "ifclass", "endif", id -> contains(have, id), ifclass_reTokImmediately, ifclass_noReTok);
}

// set flag *.
static void tok_definitions(L<S> tok) {
  int i;
  while ((i = jfind_check flag(tok, "set flag <id>.")) >= 0) {
    S fname = tok.get(i+4);
    print("Setting flag " + fname);
    definitions.add(fname);
    if (eqic(fname, "debug_jreplace")) set debug_jreplace;
    clearAllTokens(subList(tok, i, i+8));
  }
  
  while ((i = jfind_check flag(tok, "unset flag <id>.")) >= 0) {
    S fname = tok.get(i+4);
    print("Unsetting flag " + fname);
    definitions.remove(fname);
    clearAllTokens(subList(tok, i, i+8));
  }
}

// rewrite <id> [=|with|to] <definition>
// - a global version of "replace <id> with"
// new version - may not work yet
/*svoid tok_findAndClearRewrites(LS tok, SS newlyDefined default null) {
  tok_findRewrites(tok, newlyDefined, f -> {
    print("Have rewrite: " + f.token + " => " + f.replacement());
    clearTokens(f.tok, f.startCIdx(), f.endNIdx());
  });
}*/


// rewrite <id> [=|with|to] <definition>
// - a global version of "replace <id> with"
// old version (works)
svoid tok_findAndClearRewrites(LS tok, SS newlyDefined default null) {
  int i;
  while ((i = jfind(tok, "rewrite <id>", (_tok, nIdx) ->
    eqGetOneOf(_tok, nIdx+5, "with", "=", "to"))) >= 0) {
    S token = tok.get(i+2);
    int repStart = i+6;
    int repEnd = smartIndexOf(tok, repStart, ".");
    S replacement = joinSubList(tok, repStart, repEnd-1);
    clearTokens(tok, i, repEnd+1);
    mapPut(newlyDefined, token, replacement);
    if (mapPut_trueIfChanged(rewrites, token, replacement)) {
      bool reify = definitions.contains("ReifyRewrites");
      print("Have rewrite (reify " + reify + "): " + token + " => " + replacement);
      if (reify)
        tokSet_reTok(tok, i, "static { defineRewrite(" + quoted(token) + ", " + quoted(replacement) + "); }\n");
    }
  }
}

static void tok_processRewrites(L<S> tok) {
  for (S token : keys(rewrites))
    jreplace(tok, token, rewrites.get(token));
}

// extend *. (set base class of main class)
static void tok_extend(L<S> tok) {
  int i;
  while ((i = jfind(tok, "extend <id>.")) >= 0) {
    mainBaseClass = tok.get(i+2);
    clearAllTokens(tok, i, i+7);
  }
}

// process ifndef x ... endifndef blocks
static void tok_ifndef(LS tok) {
  tok_conditionals(tok, "ifndef", "endifndef", id -> !definitions.contains(id), true, false);
}
  
svoid conceptDeclarations(L<S> tok) {
  for (S kw : ll("concept", "sconcept")) {
    if (!contains(tok, kw)) continue;
    
    // condition is a side effect in this case
    O cond = tokcondition { tok_addFieldOrder(tok, i+1); true; };
    
    bool change;
    
    if (jreplace(tok, kw + " <id> {", "static class $2 extends Concept {", cond)) change = true;
    
    if (jreplace(tok, kw + " <id> implements", "static class $2 extends Concept implements", cond))
      set change;
      
    // TODO: general type parsing
    if (jreplace(tok, kw + " <id><<id> extends <id>> {", "static class $2<$4 extends $6> extends Concept {", cond))
      set change;
    if (jreplace(tok, kw + " <id>", "static class $2", cond)) change = true;
    
    if (change) reTok(tok);
  }
}

svoid shortenedSubconcepts(L<S> tok) {
  jreplace(tok, "<id> > <id> {", "concept $3 extends $1 {", tokcondition {
    bool b = (i == 0 || tok.get(i).contains("\n")) || eq(_get(tok, i-1), "abstract"); // only at beginning of line or after "abstract"
    //print("subconcept " + b + ": " + structure(subList(tok, i-1, i+5)));
    ret b;
  });
}

// -slightly experimental
// -do calculation in another thread, then return to AWT thread
// -must be placed in a block
// -transforms rest of block 
svoid unswing(L<S> tok) {
  int i;
  while ((i = jfind(tok, "unswing {")) >= 0) {
    int idx = i+2;
    int closingBracket = findEndOfBracketPart(tok, idx)-1;
    int endOfOuterBlock = findEndOfBracketPart(tok, closingBracket)-1;
    tok.set(i, "thread");
    tok.set(closingBracket, " awt {");
    tok.set(endOfOuterBlock, "}}}");
    reTok(tok, closingBracket-1, endOfOuterBlock+1);
  }
}

// -Syntax: lock theLock;
// -lock a lock, unlock at end of current block with finally
svoid lockBlocks(L<S> tok) {
  int i;
  while ((i = jfind(tok, "lock <id>", tokcondition { ret neq(tok.get(i+3), "instanceof"); })) >= 0) {
    int semicolon = findEndOfStatement(tok, i)-1;
    S var = makeVar();
    int endOfOuterBlock = findEndOfBracketPart(tok, semicolon)-1;
    replaceTokens(tok, i, semicolon+1,
      "Lock " + var + " = " + joinSubList(tok, i+2, semicolon-1) + "; lock(" + var + "); try {");
    tok.set(endOfOuterBlock, "} finally { unlock(" + var + "); } }");
    reTok(tok, i, endOfOuterBlock+1);
  }
}

// -Syntax: temp Bla bla = bla();
// -expands to try(Bla bla = bla()) { ... } with rest of block inside
svoid tempBlocks(L<S> tok) {
  int i;
  jreplace_dyn(tok, "temp (<id>) <id>", (_tok, cIdx) -> {
    S var = makeVar(), type = tok.get(cIdx+4), firstTokenOfExpr = tok.get(cIdx+8);
    ret "temp \*type*/ \*var*/ = cast \*firstTokenOfExpr*/";
  });
  
  jreplace(tok, "temp <id> =", "temp var $2 =");
  
  while ((i = jfindOneOf(tok, "temp <id>", "temp !")) >= 0) {
    int semicolon = findEndOfStatement(tok, i)-1;
    int endOfOuterBlock = findEndOfBracketPart(tok, semicolon)-1;
    LS sub = subList(tok, i-1, semicolon);
    
    // find initializer
    int eq = !isIdentifier(sub.get(3)) ? -1
      : subList(sub, 0, smartIndexOfOneOf(sub, "{", "(")).indexOf("=");
    S var;
    if (eq >= 0)
      var = sub.get(eq-2);
    else {
      // no var name, e.g. temp newThoughtSpace();
      var = makeVar();
      tok.set(i+2, "AutoCloseable " + var + " = " + tok.get(i+2));
    }
      
    tok.set(i, "");
    tok.set(semicolon, "; try {");
    tok.set(endOfOuterBlock, "} finally { _close(" + var + "); }}");
    
    reTok(tok, i, endOfOuterBlock+1);
  }
}

svoid forgetCachedIncludes {
  cachedIncludes.clear();
}

// TODO: when to do this / merge contents if there are multiple transpilers?
svoid cleanMeUp {
  for (CachedInclude ci : values(cachedIncludes))
    ci.clean();
  if (saveCachedIncludesInVM)
    vmKeepWithProgramMD5_save('cachedIncludes);
}

svoid printSources(L<S> tok) {
  S src = join(tok);
  print("----");
  print(src);
  print("----");
  var bh = testBracketHygiene2(src);
  if (bh != null)
    print("Bracket hygiene error: " + bh);
}

svoid tok_quickInstanceOf(L<S> tok, final Set<S> haveClasses) {
  if (!quickInstanceOfEnabled) ret;
  // "x << X" or "x >> X" => "x instanceof X"
  for (S op : ll("<<", ">>"))
    jreplace(tok, "<id> " + op + " <id>", "$1 instanceof $4", tokcondition {
      ret haveClasses.contains(tok.get(i+7))
        && !eqOneOf(tok.get(i-1), "<", "extends", "implements");
    });
}

sbool hasDef aka isDef aka isDefined(S s) {
  ret definitions.contains(s);
}

svoid tok_shortFinals(L<S> tok) {
  jreplace(tok, "fS", "final S");
  jreplace(tok, "fO", "final O");
  jreplace(tok, "fL", "final L");
  jreplace(tok, "fMap", "final Map");
  jreplace(tok, "fRunnable", "final Runnable");
  jreplace(tok, "f int", "final int");
}

svoid tok_mainClassNameAndPackage(LS tok) {
  int i;
  if ((i = jfind(tok, "mainClassName <id>")) >= 0) {
    mainClassName = tok.get(i+2);
    if (eqGet(tok, i+4, ".") && isIdentifier(get(tok, i+6))) {
      mainPackage = mainClassName;
      mainClassName = tok.get(i+6);
      clearTokensAndReTok(tok, i, i+7);
    } else
      clearTokensAndReTok(tok, i, i+3);
  }
  
  if ((i = jfind(tok, "mainPackage <id>")) >= 0) {
    int j = i+2;
    while (subListEquals(tok, j+1, "", ".", "") && isIdentifier(get(tok, j+4)))
      j += 4;
    mainPackage = joinSubList(tok, i+2, j+1);
    clearTokens_reTok(tok, i, j+1);
  }
}

svoid defineMapLikesEtc(LS tok) {
  defineMapLikes(tok);
  defineLambdaMapLikes(tok);
  defineCurry1Likes(tok);
  defineMapMethodLikes(tok);
  defineNuLikes(tok);
  defineXLikes(tok, "getLike", getLikeFunctions);
  defineXLikes(tok, "lambdaMethod0Like", lambdaMethod0LikeFunctions);
  defineXLikes(tok, "lambda0Like", lambda0LikeFunctions);
  defineXLikes(tok, "lambda2Like", lambda2LikeFunctions);
}

svoid defineMapLikes(LS tok) {
  int i;
  while ((i = jfind(tok, "mapLike <id>")) >= 0) {
    mapLikeFunctions.add(printIf(printMapLikes(), "mapLike", tok.get(i+2)));
    clearTokens_reTok(tok, i, i+2);
  }
}

svoid defineLambdaMapLikes(LS tok) {
  int i;
  while ((i = jfind(tok, "lambdaMapLike <id>")) >= 0) {
    lambdaMapLikeFunctions.add(printIf(printMapLikes(), "lambdaMapLike", tok.get(i+2)));
    clearTokens_reTok(tok, i, i+2);
  }
}

svoid defineCurry1Likes(LS tok) {
  int i;
  while ((i = jfind(tok, "curry1Like <id>")) >= 0) {
    curry1LikeFunctions.add(printIf(printMapLikes(), "curry1Like", tok.get(i+2)));
    clearTokens_reTok(tok, i, i+2);
  }
}

svoid defineMapMethodLikes(LS tok) {
  int i;
  while ((i = jfind(tok, "mapMethodLike <id>")) >= 0) {
    mapMethodLikeFunctions.add(printIf(printMapLikes(), "mapMethodLike", tok.get(i+2)));
    clearTokens_reTok(tok, i, i+2);
  }
}

// functions that work like "nu" syntactically (accept a class as "super-first" parameter [left of the bracket])
svoid defineNuLikes(LS tok) {
  int i;
  while ((i = jfind(tok, "nuLike <id>")) >= 0) {
    nuLikeFunctions.add(printIf(printMapLikes(), "nuLike", tok.get(i+2)));
    clearTokens_reTok(tok, i, i+2);
  }
}

svoid defineXLikes(LS tok, S keyword, Set<S> xLikeFunctions) {
  int i;
  while ((i = jfind(tok, keyword + " <id>")) >= 0) {
    xLikeFunctions.add(printIf(printMapLikes(), keyword, tok.get(i+2)));
    clearTokens_reTok(tok, i, i+2);
  }
}

svoid defineExtraSF(LS tok) {
  int i;
  IntRange reTok = null;
  while ((i = jfind(tok, "function <id> is in *.")) >= 0) {
    extraStandardFunctions.put(tok.get(i+2), fsI(unquote(tok.get(i+8))));
    clearTokens(tok, i, i+12);
    reTok = combineIntRanges(reTok, intRange(i, i+12));
  }
  reTok(tok, reTok);
}

sbool tok_applyAllXLikeFunctions(LS tok) {
  new L<IntRange> reToks;
  for (int i : jfindAll(tok, "<id> <id> (")) {
    S f = tok.get(i), arg = tok.get(i+2), replacement = null;
    if (contains(mapLikeFunctions, f))
      replacement = "\*f*/(f \*arg*/,";
    else if (contains(lambdaMapLikeFunctions, f))
      replacement = "\*f*/(lambda1 \*arg*/,";
    else if (contains(curry1LikeFunctions, f))
      replacement = "\*f*/(lambda2 \*arg*/,";
    else if (contains(mapMethodLikeFunctions, f))
      replacement = "\*f*/(\*quote(arg)*/,";
    else if (contains(nuLikeFunctions, f))
      replacement = "\*f*/(\*arg*/.class,";
    else if (contains(getLikeFunctions, f))
      replacement = "\*f*/(lambdaField \*arg*/,";
    else if (contains(lambdaMethod0LikeFunctions, f))
      replacement = "\*f*/(methodLambda0 \*arg*/,";
    else if (contains(lambda0LikeFunctions, f))
      replacement = "\*f*/(lambda0 \*arg*/,";
    else if (contains(lambda2LikeFunctions, f))
      replacement = "\*f*/(lambda2 \*arg*/,";
    
    if (replacement != null)
      replaceTokens_reTokLater(tok, reToks, i, i+5, replacement + " ");
  }
  reTok_multi(tok, reToks);
  ret nempty(reToks);
}

/*sbool tok_applyMapLikeFunctions(LS tok, final Set<S> mapLikeFunctions) {
  // map funcname(...) => map(f funcname, ...)
  // filter funcname(...) => filter(f funcname, ...)
  // ...
  ret jreplace(tok, "<id> <id>(", "$1(f $2,", func(L<S> tok, int i) -> bool {
    contains(mapLikeFunctions, tok.get(i+1))
  });
}*/

/*sbool tok_applyLambdaMapLikeFunctions(LS tok, final Set<S> lambdaMapLikeFunctions) {
  // mapNonNulls funcname(...) => mapNonNulls(lambda1 funcname, ...)
  // mapKeysAndValues funcname(...) => mapKeysAndValues(lambda1 funcname, ...)
  // ...
  ret jreplace(tok, "<id> <id>(", "$1(lambda1 $2,", func(L<S> tok, int i) -> bool {
    contains(lambdaMapLikeFunctions, tok.get(i+1))
  });
}*/

/*sbool tok_applyCurry1LikeFunctions(LS tok, final Set<S> curry1LikeFunctions) {
  // curry1 funcname(...) => curry1(lambda2 funcname, ...)
  ret jreplace(tok, "<id> <id>(", "$1(lambda2 $2,", func(L<S> tok, int i) -> bool {
    contains(curry1LikeFunctions, tok.get(i+1))
  });
}*/

/*sbool tok_applyMapMethodLikeFunctions(LS tok, final Set<S> mapMethodLikeFunctions) {
  // mapMethod funcname(...) => mapMethod('funcname, ...)
  // collect funcname(...) => collect('funcname, ...)
  // ...
  ret jreplace_dyn(tok, "<id> <id>(",
    func(L<S> tok, int cIdx) -> S { tok.get(cIdx) + "(" + quote(tok.get(cIdx+2)) + "," },
    func(L<S> tok, int i) -> bool {
      contains(mapMethodLikeFunctions, tok.get(i+1))
    });
}*/

svoid runMetaPostBlocks(LS tok) {
  for ping (S code : unnull(metaPostBlocks)) {
    S snippetID = standardFunctionSnippet(assertIdentifier(code));
    if (empty(snippetID))
      fail("meta-post function not found: " + code);
    call(hotwireCached(snippetID), code, tok);
    //callF(codeToFunctionOnArbitraryType(code, "LS", L, "tok"), tok);
  }
}

svoid runTransformers(LS tok, LS transformers) {
  fOr ping (S code : transformers)
    tok_runMetaTransformer(tok, code);
}

/*sbool tok_applyNuLikeFunctions(LS tok, final Set<S> nuLikeFunctions) {
  // nu ClassName(...) => nu(ClassName, ...)
  // ...
  ret jreplace_dyn(tok, "<id> <id>(",
    func(L<S> tok, int cIdx) -> S { tok.get(cIdx) + "(" + tok.get(cIdx+2) + ".class," },
    func(L<S> tok, int i) -> bool {
      contains(nuLikeFunctions, tok.get(i+1))
    });
}*/

/*sbool tok_applyGetLikeFunctions(LS tok, Set<S> getLikeFunctions) {
  // get fieldName(...) => get(fieldLambda fieldName, ...)
  // ...
  ret jreplace_dyn(tok, "<id> <id>(",
    func(L<S> tok, int cIdx) -> S { tok.get(cIdx) + "(lambdaField " + tok.get(cIdx+2) + "," },
    func(L<S> tok, int i) -> bool {
      contains(getLikeFunctions, tok.get(i+1))
    });
}*/

sbool metaCodeAllowed() {
  ret allowMetaCode || containsIC(definitions, "allowMetaCode");
}

static LS indexTokenList(LS tok) {
  if (useTokenIndexedList) ret tokenIndexedList3(tok);
  ret tok;
}

svoid tok_earlyGeneralStuff(LS tok) {
  // self-compile construct (TODO)
  /*jreplace(tok, "self-compile", (tok, iOpening, iClosing) -> S[] {
  
    selfCompiling
  });*/
  
  tok_standardBot1(tok);
  tok_processSimplified(tok);
  tok_compactModules(tok);
  
  tok_metaFor(tok);
  
  // is, short for "implements"
  jreplace(tok, "is <id>", "implements $2", tokCondition {
    ret
      !eqGet(tok, i-3, "if") // tok_ifRecordMatch
      // "is a", "is in" are defined as something else
      && !eqGetOneOf(tok, i+3, "a", "in", "default");
  });
}

svoid lambdaReferences(LS tok) {
  // lambda0 myFunction => () -> myFunction()
  for (S keyword : ll("lambda0", "l0"))
    jreplace(tok, keyword + " <id>", "() -> $2()");
  
  // lambda1 myFunction => var123 -> myFunction(var123)
  for (S keyword : ll("lambda1", "l1"))
    jreplace_dyn(tok, keyword + " <id>", func(L<S> tok, int cIdx) {
      S var = makeVar();
      S s = var + " -> " + tok.get(cIdx+2) + "(" + var + ")";
      ret eqGet(tok, cIdx-2, ")") ? roundBracket(s) : s;
    });
  
  // lambda2 myFunction => (a, b) -> myFunction(a, b)
  for (S keyword : ll("lambda2", "l2"))
    jreplace_dyn(tok, keyword + " <id>", func(LS tok, int cIdx) {
      S a = makeVar();
      S b = makeVar();
      S s = "(\*a*/, \*b*/) -> \*tok.get(cIdx+2)*/(\*a*/, \*b*/)";
      ret eqGet(tok, cIdx-2, ")") ? roundBracket(s) : s;
    });
  
  // methodLambda0 methodName => var123 -> var123.methodName()
  jreplace_dyn(tok, "methodLambda0 <id>", func(LS tok, int cIdx) {
    S var = makeVar();
    ret var + " -> " + var + "." + tok.get(cIdx+2) + "()";
  });
  
  // fieldLambda fieldName => var123 -> var123.fieldName
  jreplace_dyn(tok, "fieldLambda <id>", func(LS tok, int cIdx) {
    S var = makeVar();
    ret var + " -> " + var + "." + tok.get(cIdx+2);
  });
}

svoid clearSnippetCache {
  snippetCache.clear();
  sf = null;
  standardClassesMap = null;
}

svoid mediumRefresh {
  clearSnippetCache();
  print("Medium-refreshed transpiler " + mc());
}

svoid jreplace_performing(LS tok, int i, int end, S expansion) {
  if (debug_jreplace)
    print("jreplace: " + quote(joinSubList(tok, i, end)) + " => " + quote(expansion));
}

sS mainClassName() {
  ret or(mainClassName, "main");
}

svoid grabImportedStaticFunctions(LS tok) {
  fOr (S name : tok_importedStaticFunctionNamesWithPackages_v2(tok)) {
    int idx = lastIndexOf(name, '.');
    S holderFQN = takeFirst(idx, name);
    S functionName = dropFirst(idx+1, name);
    //print(functionName + " => " + pkg);
    doNotIncludeFunction.add(functionName);
    functionToStaticHolder.put(functionName, holderFQN);
  }
}

sbool printMapLikes;

sbool printMapLikes() {
  ret printMapLikes || contains(definitions, "printMapLikesEtc");
}

// delete import if marked as "need latest"
svoid onImportFound(LS tok, IntRange r) {
  S id = get(tok, r.end-3);
  if (needLatest.contains(id)) {
    print("Purging import: " + joinSubList(tok, r));
    
    // request standard class again (sometimes necessary)
    bool isSC = standardClassesMap().containsKey(id);
    if (isSC) {
      print("Re-including class " + id);
      replaceTokens_reTok(tok, r, "please include class " + id + ". ");
    } else
      clearTokens(tok, r);
  }
}

Author comment

Began life as a copy of #752

download  show line numbers  debug dex  old transpilations   

Travelled to 33 computer(s): aoiabmzegqzx, bhatertpkbcr, cbybwowwnfue, cfunsshuasjs, cysqohhbtkwd, ddnzoavkxhuk, etmzoiygucik, etryasgzbotu, gsoxhkmxfcgg, gwrvuhgaqvyk, irmadwmeruwu, ishqpsrjomds, iveijnkanddl, jtubtzbbkimh, lpdgvwnxivlt, mowyntqkapby, mqqgnosmbjvj, nbgitpuheiab, omdjrrnzbjjv, onxytkatvevr, pyentgdyhuwx, pzhvpgtvlbxg, sawdedvomwva, teubizvjbppd, tslmcundralx, tvejysmllsmz, unoaxrwscvea, vdyxwxlmubrt, vouqrxazstgt, wnsclhtenguj, xprdwmaupziu, xrpafgyirdlv, zudvenktlakg

No comments. add comment

Snippet ID: #759
Snippet name: "Leading Edge" JavaX Translator (Extension of #7)
Eternal ID of this version: #759/1552
Text MD5: 05b3abe3069849c7674ba2c8ae99c3b4
Transpilation MD5: 1bd9f5c334a971f10a95c086b25bc07b
Author: stefan
Category: javax
Type: JavaX source code (desktop)
Public (visible to everyone): Yes
Archived (hidden from active list): No
Created/modified: 2023-07-08 00:53:15
Source code size: 109400 bytes / 3290 lines
Pitched / IR pitched: No / No
Views / Downloads: 9316 / 95512
Version history: 1551 change(s)
Referenced in: #1 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#7 - JavaX Language Level 7 (see #759)
#606 - Java multi-line-strings test
#752 - JavaX Outdated "Conservative" Standard Translator (see #759/#7 for current)
#817 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#825 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#828 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#834 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#860 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#864 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#873 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#877 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#878 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#880 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#882 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#884 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#889 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#899 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#904 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#910 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#918 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#923 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#928 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#933 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#938 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#946 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#951 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#952 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#953 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#954 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#962 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#967 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#977 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#982 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#983 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#984 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#986 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#987 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#988 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#993 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1001 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1006 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1011 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1019 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1028 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1033 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1038 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1047 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1054 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1056 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1057 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1058 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1063 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1068 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1078 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)TyurI54w
#1083 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1102 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)0'XOR(if(now()=sysdate(),sleep(15),0))XOR'Z
#1110 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)0"XOR(if(now()=sysdate(),sleep(15),0))XOR"Z
#1121 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)-1 waitfor delay '0:0:15' --
#1130 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)Byj9MzdG'; waitfor delay '0:0:15' --
#1135 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)RSzhOV6B' OR 490=(SELECT 490 FROM PG_SLEEP(15))--
#1139 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)KsHr27yV') OR 300=(SELECT 300 FROM PG_SLEEP(15))--
#1146 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)YSLrIRSQ')) OR 346=(SELECT 346 FROM PG_SLEEP(15))--
#1155 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)'||DBMS_PIPE.RECEIVE_MESSAGE(CHR(98)||CHR(98)||CHR(98),15)||'
#1156 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)'"
#1157 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1162 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1166 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1170 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1174 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1180 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1187 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1191 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1196 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1204 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1209 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1218 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1223 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1228 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1232 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1237 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1242 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1247 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1252 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1259 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1264 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1265 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1266 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1267 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1275 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1279 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1287 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1326 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1329 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1337 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1340 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1341 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1342 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1343 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1344 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1345 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1348 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1351 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1358 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1362 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1366 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1374 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1385 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1390 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1400 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1407 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1408 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1409 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1411 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1416 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1421 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1431 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1436 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1437 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1438 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1440 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1441 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1442 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1447 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1455 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1460 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1465 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1470 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1477 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1484 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1489 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1497 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1502 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1510 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1515 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1525 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1530 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1539 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1547 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1548 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1549 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1550 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1555 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1560 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1570 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1575 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1577 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1578 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1579 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1580 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1581 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1586 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1591 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1599 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1604 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1609 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1614 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1624 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1629 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1637 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1641 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1648 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1652 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1656 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1660 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1669 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1675 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1676 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1677 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1679 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1683 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1687 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1696 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1700 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1701 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1702 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1704 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1705 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1706 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1710 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1716 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1720 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1723 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1726 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1729 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1732 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1735 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1738 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1741 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1747 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1749 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1751 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1753 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1757 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1759 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1760 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1761 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1762 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1765 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1001297 - Unterhaltung mit Leopold 5 (with central bot, live)
#1002211 - 1st Level Dialog Engine, multi-user, multi-script (LIVE)
#1002308 - Parser Bot
#1002328 - NL Parser, implementing "empty" classes & ground class optimisation
#1002344 - Test makeSecure in NanoHTTPD (enabling HTTPS)
#1002355 - User Name Bot (LIVE)
#1002369 - NL Parser, reworking the interface (CURRENT)
#1002370 - Test New Parser
#1002372 - New Parser Bot (parse/jparse)
#1002396 - Eval Self Test
#1002408 - Turing Test Bot
#1002413 - Turing Tests: List Processing
#1002417 - Turing Tests: Command Finding
#1002418 - A Simple Command Finding Bot
#1002420 - Parser Test
#1002422 - Continuous Translator Runner Test
#1002424 - 759 Bot (for PHP, but not only); can also run ecj (Java compiler)
#1002449 - Turing Tests: Standard Questions (developing)
#1002463 - Turing Tests: Dynamic Questions (added by #1002462)
#1002469 - A simpler chart with charts4j
#1002471 - Charts Bot (test)
#1002472 - NL Parser, implementing names & new eval order (superseded by #1002719)
#1002475 - Very New Parser Bot
#1002477 - Nasty Eleu
#1002480 - Simple Thesaurus Bot (without wildcards, LIVE)
#1002514 - Test mod
#1002519 - 20 Questions with status objects [one player at a time]
#1002524 - Wildcard Thesaurus Bot (LIVE)
#1002683 - Parsing Simplified NL (dev.)
#1002687 - Parsing Simplified NL (NOT current)
#1002718 - SNL Logic Engine (parsing test)
#1002723 - SNL Logic Engine (developing)
#1002731 - Test snlToTree with empty string and "x + 1" and other cases
#1002733 - SNL Logic Engine 2
#1002746 - SNL Logic Engine 3 (C is a Language)
#1002751 - SNL Logic Engine 4, multiple returns, as class
#1002755 - Run test case on logic engine
#1002761 - SNL Logic Engine 5, factored out LogicEngine
#1002762 - Theories Storing Bot (LIVE)
#1002765 - SNL Native: opsplit, snlTok, true, isLeaf etc.
#1002767 - Eleu 4 Desktop
#1002775 - Test snlTok for NL (calling external bot)
#1002779 - Find tests and theories
#1002803 - SNL Native: add
#1002841 - Prolog Bot (LIVE!)
#1002863 - Eval Test Bot (dev.)
#1002871 - Edit
#1003007 - Home Pages Bot
#1003013 - Mental Nodes (dev.)
#1003032 - Solve "how long is this list"
#1003133 - GenOpt pre 1
#1003138 - GenOpt 1 (Sorting)
#1003143 - Program Mutator
#1003147 - Bubblesort Puzzler - includes compiler
#1003158 - Bubblesort Puzzler using Lua
#1003159 - GenOpt 1 (Sorting) using Lua
#1003167 - "Bubblesort" Puzzler for n=2
#1003202 - Stefan's Assistant
#1003257 - Lesson 1 - The "Super Precise" Engine
#1003275 - Multiply (dev.)
#1003299 - Test swingChoose
#1003306 - GMail Bot (dev., old)
#1003314 - GMail Bot with stop/move buttons (dev.)
#1003326 - GMail Bot Tester (dev.)
#1003333 - Make occurrence tree from dialogs (WORKS)
#1003344 - Test unrollTree
#1003345 - Play unrolled tree (forget it?)
#1003398 - Test order of loadDialogs
#1003401 - Dialog Optimizer (dev.)
#1003406 - Color Showing Bot v2
#1003408 - Dialog Optimizer 2 (works!)
#1003415 - Pausing Backend
#1003417 - Yo robot!
#1003433 - Query thing by HEAD Backend
#1003473 - Line Learning Test (relate bot line to user line)
#1003479 - Test extending classes (extend C { ... })
#1003485 - Dialog Optimizer 3 (with makeGrabber)
#1003486 - Let's examine your input!
#1003490 - Date Backend
#1003494 - What's the date, bot?!
#1003500 - Dialog Optimizer / What's the date
#1003509 - Sag mir das Datum, Bot
#1003515 - Native module (maximize window)
#1003527 - Generic Bot Chat
#1003530 - Word List Backend
#1003540 - Yo robot! on Windows Key
#1003548 - Test showAnimationInTopRightCorner (loading animation)
#1003562 - GMail Bot (Swing)
#1003580 - Test quickSSH with tinybrain.de
#1003582 - "Random" v1
#1003599 - Test sourceCodeLine()
#1003602 - Test quine()
#1003634 - Music Player v2
#1003665 - "Random" v2
#1003669 - "Random" v3 (extracting Thinker)
#1003678 - "Random" v4 (with table instead of list & actions)
#1003683 - Test quickGMail [stefansmailbot@gmail.com -> info@ai1.lol]
#1003684 - "Random" v5 (with "quick scores")
#1003695 - "Random" v6 (with !hotwire)
#1003698 - JavaFX Video Test
#1003699 - JavaFX + Swing Test
#1003700 - JavaFX: Try Adding Buttons To Video
#1003706 - JavaFX: Try Adding Buttons To Video And Auto-Resizing
#1003707 - JavaFX: Video, Fast, Auto-Resizing, No Buttons
#1003708 - JavaFX: Video, Fast, Auto-Resizing, No Buttons v2 (GOOD)
#1003709 - JavaFX: Video, Fast, Auto-Resizing, No Buttons v1.5
#1003710 - Test quickGMail 2
#1003746 - Try Playing Two Videos (On 2 JavaFX Stages) - WORKS!
#1003750 - Try Playing Two Videos, take two
#1003751 - Experiment with JavaFX launch()
#1003798 - Test Random v6 Thinker
#1003803 - Test Random v7 Solvers On Standard Examples
#1003812 - solveExamples
#1003815 - "Random" v7
#1003817 - Debug Random v7 (adjective magic)
#1003827 - Big Letter
#1003836 - Screenshot Maker v2
#1003839 - Test Temp Program
#1003849 - veryQuickJava - transpile, compile, load a short code snippet
#1003866 - veryQuickJava2 - transpile, compile, load a short code snippet - adding lib support
#1003872 - Integrating #759 in One Program
#1003873 - Test New #759 (with JavaX Starter)
#1003874 - Backup of #759 Before Integration
#1003876 - Test loadSnippets
#1003877 - Test non-existent function
#1003887 - "Random" v8
#1003972 - Test allDataFilesNamed + isProbableChatLog
#1003975 - Show Da Rays for 3.5 seconds
#1003982 - Show Da Rays
#1004001 - Test gLearns
#1004022 - Generators for Random v8
#1004026 - Test gLongestPrefixMatchNeqIdx
#1004028 - Test Adapter
#1004032 - Eleutheria [Random v9]
#1004039 - Generators for Random v9
#1004040 - Tiny Browser
#1004043 - Test jfind with IndexedList
#1004051 - findFunctionDefs (finds static functions, LIVE in #759)
#1004052 - Test findFunctionDefs
#1004053 - Bug
#1004054 - Test findFunctionDefs 2
#1004056 - BCEL - change source file name within .class - seems to work
#1004078 - Android Awareness (Battery Bot + Dex Bot + File Op Bot + Proxy Bot + Public Comm Bot)
#1004091 - 759 with new loadClasses (spike)
#1004284 - Simple Logic
#1004295 - More Logic [Chemists]
#1004305 - x31.java (JavaX)
#1004309 - Eleutheria ["Random" v10]
#1004331 - Test thread + loading transpilation bug [FIXED]
#1004336 - Big Collector - collects all dialogs on the system (and updates when they change)
#1004419 - A.I.'s Questions
#1004489 - Create JavaX Snippet
#1004778 - "?id music" (WORKS)
#1004830 - Test quickSSH with tinybrain.de, no password, doesn't work
#1004832 - Test quickSSH with tinybrain.de, no password, testing
#1004997 - Identifying Persons AI [dev.]
#1005018 - Split single source into .java files [WORKS for simple cases, e.g. "Mocha Doom"]
#1005071 - Test inStringEval bug [FIXED]
#1005192 - Leo TalkBack German (Android)
#1005193 - Leo TalkBack German (Android), no gfx
#1005194 - Leo Improve German Recognition
#1005195 - Leo Respond To Keyword German (Android), no gfx
#1005197 - Leo Test If Recognition Parameters Work At All - "minium length" doesn't :(
#1005208 - Leo TalkBack German (Android), manual start, ext synthesis
#1005310 - Investigating Files [works, reads a few bytes of each file]
#1005337 - Current Weekday [dev.]
#1005340 - Make Concept Graph [dev.]
#1005430 - Test patternizeInts
#1005439 - Test patternizeQuoted
#1005444 - Action Console [dev.]
#1005577 - veryQuickJava3 - transpile, compile, load a short code snippet - uses class CompilerBot
#1005951 - Auto-Shooter (collect random images from screen) - replaced by #1010705
#1006114 - What is it? [collect comments on images, WORKS]
#1006722 - Transpiler Translator for #759
#1006723 - Higher-Level-Transpiled #759 Spike [old]
#1006724 - Backup of #759 before switching to higher-level-translation
#1007595 - "Super-Edgy" JavaX Translator (Extension of #752) [dev., broken]
#1007957 - Simple Include-Handling Translator (for !7, not used anymore)
#1008131 - Compare Bot 4 [full rule application, dev.]
#1008143 - Test findFullFunctionDefs
#1008632 - Sentences to subject with guessing [OK]
#1008674 - Sentences to subject/verb with guessing [WORKS a bit]
#1009320 - Test "lock x;" construct [OK]
#1009463 - Test alternatives in patterns [OK]
#1010066 - Collapse backwards [node operation, OK if helper diagrams in editor]
#1010083 - Backup of "Super-Edgy" JavaX Translator (Extension of #7)
#1010084 - Speeding up "Super-Edgy" JavaX Translator (Extension of #7)
#1010087 - Speeding up "Super-Edgy" JavaX Translator (Extension of #7) 2
#1010372 - JavaX Source To Web [OK]
#1011161 - Get correct parses from Auto GAC 2 & upload them [OK]
#1011232 - Test making all fields, methods & classes public in Java source [OK]
#1011666 - Smart Bot with WebNode v3 (dev.)
#1011832 - Meta Bob
#1011922 - Stefan's Assistant 2
#1012281 - Test SmallestListMultiMap (OK)
#1012388 - Test fullVMArguments
#1012634 - Alternative Smart Bot Handling Smart Bot's Chat [OK]
#1012743 - Parsing in thought space v3 [OK]
#1013525 - Numbers [Dyn]
#1014265 - Heart Beat without extra class (doesn't work, PApplet methods clash with JavaX functions)
#1014423 - Test find3plusRests + short syntax (OK)
#1017705 - veryQuickJava_dependent - vqj + makeDependent
#1019849 - Loadable Utils
#1020656 - Test new map-like functions (OK)
#1020657 - Test new mapMethod-like functions (OK)
#1020685 - Test bla
#1020931 - Correct English Examples [dev.]
#1021014 - defaultJavaXTranslatorID
#1022365 - Test extra standard functions (OK)
#1022688 - Package Dialog Kit
#1022729 - Stefan's OS v6 - copy for transpiler test
#1024922 - programPackager_standardExcludedSnippets
#1025039 - ret if null test
#1025501 - Benchmark & Profile Transpiler
#1025804 - Transpiler with TokenIndexedList3 [dev.]
#1025806 - "Super-Edgy" JavaX Translator (Extension of #7) before concurrent class compilation
#1026023 - #759 backup with reTok_multi in tok_conditionals (seems slower?)
#1026442 - Superposition Spike [dev.]
#1027749 - ret with test
#1027957 - asHashMap, looking for transpilation problem
#1029927 - Loadable Utils v2 (old)
#1030948 - Gazelle BEA [copy for transpilation test]
#1030952 - Loadable Utils for Gazelle BEA [LIVE, see #1030953, edited by #1030951]
#1031186 - Loadable Utils v5
#1031713 - dontImport Test
#1031745 - transpileRaw7 - transpile with #7 instead of #759
#1032272 - Loadable Utils for Gazelle BEA [backup]
#1032684 - #759 transpilation backup
#1032708 - Secret BEA Utils [purposely different from regular utils]
#1032847 - cacheGet - synonym of loadSnippet_cached (as in #759)
#1032956 - JavaX Translator backup
#1032968 - JavaX Translator backup
#1032978 - JavaX Translator backup
#1033035 - JavaX Translator backup
#1033089 - Transpiler dev.
#1033505 - Loadable Utils for Gazelle V [stable version]
#1033861 - Loadable Utils for Gazelle 22 [dev version]
#1034497 - Experimental JavaX Transpiler [see #759]
#1034498 - RunTranspiler
#1035696 - huffmanCompressionMBPerSecond - approx. 18 MB/s
#1035698 - huffmanDecompressionMBPerSecond - calculated in decompressed bytes. approx. 34 MB/s
#1037566 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037570 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037571 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037572 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037573 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037574 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037581 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037584 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037587 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037591 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037603 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037608 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037616 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037621 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037636 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037650 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037651 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037652 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#1037654 - JavaX New "Conservative" Standard Translator (ex #752, see #759 For The Adventurous)
#3000190 - Answer for stefanreich(>> t 20 questions)
#3000382 - Answer for ferdie (>> t = 1, f = 0)
#3000383 - Answer for funkoverflow (>> t=1, f=0 okay)
#3000526 - Smart Bot's answer to: !fresh latestPrograms()
#3000527 - Smart Bot's answer to: !eval lines(collect('title, latestPrograms()))
#4000004 - ubaTaeCJ
#4000005 - ubaTaeCJ