

#jmp_buf stop_return, draw_stop_return

# s is a string here
stop = (s) ->
  #if (draw_flag == 2)
  #  longjmp(draw_stop_return, 1)
  #else
    errorMessage += "Stop: "
    errorMessage += s
    #debugger
    message = errorMessage

    errorMessage = ''
    moveTos 0

    throw new Error(message)
    
    #longjmp(stop_return, 1)

# Figuring out dependencies is key to automatically
# generating a method signature when generating JS code
# from algebrite scripts.
# This is important because the user can keep using normal Algebrite
# scripting without special notations.
# Basically the process consists of figuring out
# the "ground variables" that are needed to compute each variable.
# Now there are two ways of doing this:
#   * at parse time
#   * after running the scripts
# Doing it at parse time means that we can't track simplifications
# canceling-out some variables for example. But on the other side
# it's very quick and the user can somehow see what the signature is
# going to look like (assuming tha code is rather simple), or anyways
# is going to easily make sense of the generated signature.
# Doing it after execution on the other hand would allow us to see
# if some variable cancel-out. But if variables cancel out then
# they might do so according to some run-time behaviour that the user
# might struggle to keep track of.
# So the effort for the user to make sense of the signature in the first case
# is similar to the effort of keeping tab of types in a typed language.
# While in the second case the effort is similar to running the
# code and simplifications in her head.
# 
# If we just want to compute the dependencies, we don't need to do
# anything costly, we don't "run" the code and we don't simplify
# the code. Just finding the plain dependencies
# TODO change the name of this function, as it doesn't just find the
# dependencies. It also runs it and generates the JS code.
findDependenciesInScript = (stringToBeParsed, dontGenerateCode) ->

  if DEBUG then console.log "stringToBeParsed: " + stringToBeParsed

  timeStartFromAlgebra  = new Date().getTime()

  inited = true
  codeGen = true
  symbolsDependencies = {}
  symbolsHavingReassignments = []
  symbolsInExpressionsWithoutAssignments = []
  patternHasBeenFound = false
  indexOfPartRemainingToBeParsed = 0

  allReturnedPlainStrings = ""
  allReturnedLatexStrings = ""

  n = 0

  # we are going to store the dependencies _of the block as a whole_
  # so all affected variables in the whole block are lumped
  # together, and same for the variable that affect those, we
  # lump them all together.
  dependencyInfo =
    affectsVariables: []
    affectedBy: []


  stringToBeRun = stringToBeParsed


  # parse the input. This collects the
  # dependency information
  while (1)
    try
      errorMessage = ""
      check_stack()
      if DEBUG then console.log "findDependenciesInScript: scanning"
      n = scan(stringToBeParsed.substring(indexOfPartRemainingToBeParsed))
      if DEBUG then console.log "scanned"
      pop()
      check_stack()
    catch error
      if PRINTOUTRESULT then console.log error
      errorMessage = error + ""
      #debugger
      reset_after_error()
      break

    if (n == 0)
      break

    indexOfPartRemainingToBeParsed += n

  testableString = ""

  # print out all local dependencies as collected by this
  # parsing pass
  if DEBUG then console.log "all local dependencies ----------------"
  testableString += "All local dependencies: "
  for key, value of symbolsDependencies
    if DEBUG then console.log "variable " + key + " depends on: "
    dependencyInfo.affectsVariables.push key
    testableString +=  " variable " + key + " depends on: "
    for i in value
      if DEBUG then console.log "    " + i
      if i[0] != "'"
        dependencyInfo.affectedBy.push i
      testableString +=  i + ", "
    testableString += "; "
  testableString += ". "

  # print out the symbols with re-assignments:
  if DEBUG then console.log "Symbols with reassignments ----------------"
  testableString += "Symbols with reassignments: "
  for key in symbolsHavingReassignments
    if dependencyInfo.affectedBy.indexOf(key) == -1
      dependencyInfo.affectedBy.push key
      testableString +=  key + ", "
  testableString += ". "

  # print out the symbols that appear in expressions without assignments
  if DEBUG then console.log "Symbols in expressions without assignments ----------------"
  testableString += "Symbols in expressions without assignments: "
  for key in symbolsInExpressionsWithoutAssignments
    if dependencyInfo.affectedBy.indexOf(key) == -1
      dependencyInfo.affectedBy.push key
      testableString +=  key + ", "
  testableString += ". "

  # ALL Algebrite code is affected by any pattern changing
  dependencyInfo.affectedBy.push "PATTERN_DEPENDENCY"

  if patternHasBeenFound
    dependencyInfo.affectsVariables.push "PATTERN_DEPENDENCY"
    testableString += " - PATTERN_DEPENDENCY inserted - "

  # print out all global dependencies as collected by this
  # parsing pass
  if DEBUG then console.log "All dependencies recursively ----------------"
  testableString += "All dependencies recursively: "

  scriptEvaluation = ["",""]
  generatedCode = ""
  readableSummaryOfGeneratedCode = ""

  if errorMessage == "" and !dontGenerateCode

    try
      allReturnedPlainStrings = ""
      allReturnedLatexStrings = ""
      scriptEvaluation = run(stringToBeParsed, true)
      allReturnedPlainStrings = ""
      allReturnedLatexStrings = ""
    catch error
      if PRINTOUTRESULT then console.log error
      errorMessage = error + ""
      #debugger
      init()

    if errorMessage == ""
      for key of symbolsDependencies


        codeGen = true
        if DEBUG then console.log "  variable " + key + " is: " + get_binding(usr_symbol(key)).toString()
        codeGen = false
        if DEBUG then console.log "  variable " + key + " depends on: "
        testableString +=  " variable " + key + " depends on: "

        recursedDependencies = []
        variablesWithCycles = []
        cyclesDescriptions = []

        recursiveDependencies key, recursedDependencies, [], variablesWithCycles, [], cyclesDescriptions

        for i in variablesWithCycles
          if DEBUG then console.log "    --> cycle through " + i

        for i in recursedDependencies
          if DEBUG then console.log "    " + i
          testableString +=  i + ", "
        testableString += "; "

        for i in cyclesDescriptions
          testableString += " " + i + ", "

        if DEBUG then console.log "  code generation:" + key + " is: " + get_binding(usr_symbol(key)).toString()

        # we really want to make an extra effort
        # to generate simplified code, so
        # run a "simplify" on the content of each
        # variable that we are generating code for.
        # Note that the variable
        # will still point to un-simplified structures,
        # we only simplify the generated code.
        push get_binding(usr_symbol(key))

        # Since we go and simplify all variables we meet,
        # we have to replace each variable passed as a parameter
        # with something entirely new, so that there is no chance
        # that it might evoke previous values in the external scope
        # as in this case:
        #  a = 2
        #  f(a) = a+1+b
        # we don't want 'a' in the body of f to be simplified to 2
        # There are two cases: 1) the variable actually was already in
        # the symbol table, in which case there is going to be this new
        # one prepended with AVOID_BINDING_TO_EXTERNAL_SCOPE_VALUE, and
        # we'll have to remove up this variable later.
        # OR 2) the variable wasn't already in the symbol table, in which
        # case we directly create this one, which means that we'll have
        # to rename it later to the correct name without the prepended
        # part.

        replacementsFrom = []
        replacementsTo = []

        for eachDependency in recursedDependencies
          if eachDependency[0] == "'"
            deQuotedDep = eachDependency.substring(1)
            originalUserSymbol = usr_symbol(deQuotedDep)
            newUserSymbol = usr_symbol("AVOID_BINDING_TO_EXTERNAL_SCOPE_VALUE"+deQuotedDep)
            replacementsFrom.push originalUserSymbol
            replacementsTo.push newUserSymbol
            push(originalUserSymbol)
            push(newUserSymbol)
            subst()
            if DEBUG then console.log "after substitution: " + stack[tos-1]

        try
          simplifyForCodeGeneration()
        catch error
          if PRINTOUTRESULT then console.log error
          errorMessage = error + ""
          #debugger
          init()

        for indexOfEachReplacement in [0...replacementsFrom.length]
          #console.log "replacing back " + replacementsTo[indexOfEachReplacement] + " into: " + replacementsFrom[indexOfEachReplacement]
          push(replacementsTo[indexOfEachReplacement])
          push(replacementsFrom[indexOfEachReplacement])
          subst()

        clearRenamedVariablesToAvoidBindingToExternalScope()

        if errorMessage == ""
          toBePrinted = pop()

          # we have to get all the variables used on the right side
          # here. I.e. to print the arguments it's better to look at the
          # actual method body after simplification.
          userVariablesMentioned = []
          collectUserSymbols(toBePrinted, userVariablesMentioned)

          allReturnedPlainStrings = ""
          allReturnedLatexStrings = ""
          codeGen = true
          generatedBody = toBePrinted.toString()
          codeGen = false

          origPrintMode = printMode
          printMode = PRINTMODE_LATEX

          bodyForReadableSummaryOfGeneratedCode = toBePrinted.toString()

          printMode = origPrintMode

          if variablesWithCycles.indexOf(key) != -1
            generatedCode += "// " + key + " is part of a cyclic dependency, no code generated."
            readableSummaryOfGeneratedCode += "#" + key + " is part of a cyclic dependency, no code generated."
          else

            ###
            # using this paragraph instead of the following one
            # creates methods signatures that
            # are slightly less efficient
            # i.e. variables compare even if they are
            # simplified away.
            # In theory these signatures are more stable, but
            # in practice signatures vary quite a bit anyways
            # depending on previous assignments for example,
            # so it's unclear whether going for stability
            # is sensible at all..
            if recursedDependencies.length != 0
              parameters = "("
              for i in recursedDependencies
                if i.indexOf("'") != 0
                  parameters += i + ", "
                else
                  if recursedDependencies.indexOf(i.substring(1)) == -1
                    parameters += i.substring(1) + ", "
            ###


            # remove all native functions from the
            # parameters as well.
            userVariablesMentioned = userVariablesMentioned.filter (x) ->
              predefinedSymbolsInGlobalScope_doNotTrackInDependencies.indexOf(x + "") == -1

            # remove the variable that are not in the dependency list
            # i.e. only allow the variables that are in the dependency list
            userVariablesMentioned = userVariablesMentioned.filter (x) ->
              recursedDependencies.indexOf(x + "") != -1 or
              recursedDependencies.indexOf("\'" + x + "") != -1

            if userVariablesMentioned.length != 0
              parameters = "("
              for i in userVariablesMentioned
                if i.printname != key
                  parameters += i.printname + ", "

              # eliminate the last ", " for printout clarity
              parameters = parameters.replace /, $/gm , ""
              parameters += ")"
              generatedCode += key + " = function " + parameters + " { return ( " + generatedBody + " ); }"
              readableSummaryOfGeneratedCode += key + parameters + " = " + bodyForReadableSummaryOfGeneratedCode
            else
              generatedCode += key + " = " + generatedBody + ";"
              readableSummaryOfGeneratedCode += key + " = " + bodyForReadableSummaryOfGeneratedCode

          generatedCode += "\n"
          readableSummaryOfGeneratedCode += "\n"

          if DEBUG then console.log "    " + generatedCode

  # eliminate the last new line
  generatedCode = generatedCode.replace /\n$/gm , ""
  readableSummaryOfGeneratedCode = readableSummaryOfGeneratedCode.replace /\n$/gm , ""


  # cleanup
  symbolsDependencies = {}
  symbolsHavingReassignments = []
  patternHasBeenFound = false
  symbolsInExpressionsWithoutAssignments = []

  if DEBUG then console.log "testable string: " + testableString

  if TIMING_DEBUGS
    console.log "findDependenciesInScript time for: " + stringToBeRun + " : "+ ((new Date().getTime()) - timeStartFromAlgebra) + "ms"

  return [testableString, scriptEvaluation[0], generatedCode, readableSummaryOfGeneratedCode, scriptEvaluation[1], errorMessage, dependencyInfo]

recursiveDependencies = (variableToBeChecked, arrayWhereDependenciesWillBeAdded, variablesAlreadyFleshedOut, variablesWithCycles, chainBeingChecked, cyclesDescriptions) ->
  variablesAlreadyFleshedOut.push variableToBeChecked

  # recursive dependencies can only be descended if the variable is not bound to a parameter
  if symbolsDependencies[chainBeingChecked[chainBeingChecked.length-1]]?
    if symbolsDependencies[chainBeingChecked[chainBeingChecked.length-1]].indexOf("'"+variableToBeChecked) != -1
      if DEBUG then console.log "can't keep following the chain of " + variableToBeChecked + " because it's actually a variable bound to a parameter"
      if arrayWhereDependenciesWillBeAdded.indexOf("'"+variableToBeChecked) == -1 and arrayWhereDependenciesWillBeAdded.indexOf(variableToBeChecked) == -1
        arrayWhereDependenciesWillBeAdded.push variableToBeChecked
      return arrayWhereDependenciesWillBeAdded

  chainBeingChecked.push variableToBeChecked

  if !symbolsDependencies[variableToBeChecked]?
    # end case: the passed variable has no dependencies
    # so there is nothing else to do
    if arrayWhereDependenciesWillBeAdded.indexOf(variableToBeChecked) == -1
      arrayWhereDependenciesWillBeAdded.push variableToBeChecked
    return arrayWhereDependenciesWillBeAdded
  else
    # recursion case: we have to dig deeper
    for i in symbolsDependencies[variableToBeChecked]

      # check that there is no recursion in dependencies
      # we do that by keeping a list of variables that
      # have already been "fleshed-out". If we encounter
      # any of those "fleshed-out" variables while
      # fleshing out, then there is a cycle 

      if chainBeingChecked.indexOf(i) != -1
        if DEBUG then console.log "  found cycle:"
        cyclesDescription = ""
        for k in chainBeingChecked
          if variablesWithCycles.indexOf(k) == -1
            variablesWithCycles.push k
          if DEBUG then console.log k + " --> "
          cyclesDescription += k + " --> "
        if DEBUG then console.log " ... then " + i + " again"
        cyclesDescription += " ... then " + i + " again"
        cyclesDescriptions.push cyclesDescription
        #if DEBUG then console.log "    --> cycle through " + i
        # we want to flesh-out i but it's already been
        # fleshed-out, just add it to the variables
        # with cycles and move on
        # todo refactor this, there are two copies of these two lines
        if variablesWithCycles.indexOf(i) == -1
          variablesWithCycles.push i
      else
        # flesh-out i recursively
        recursiveDependencies i, arrayWhereDependenciesWillBeAdded, variablesAlreadyFleshedOut, variablesWithCycles, chainBeingChecked, cyclesDescriptions
        chainBeingChecked.pop()
        #variablesAlreadyFleshedOut.pop()

    return arrayWhereDependenciesWillBeAdded



# parses and runs one statement/expression at a time
inited = false

latexErrorSign = "\\rlap{\\large\\color{red}\\bigtriangleup}{\\ \\ \\tiny\\color{red}!}"
turnErrorMessageToLatex = (theErrorMessage) ->
  theErrorMessage = theErrorMessage.replace(/\n/g,"")
  theErrorMessage = theErrorMessage.replace(/_/g, "} \\_ \\text{");
  theErrorMessage = theErrorMessage.replace(new RegExp(String.fromCharCode(transpose_unicode), 'g'), "}{}^{T}\\text{");
  theErrorMessage = theErrorMessage.replace(new RegExp(String.fromCharCode(dotprod_unicode), 'g'),"}\\cdot \\text{");
  theErrorMessage = theErrorMessage.replace("Stop:","}  \\quad \\text{Stop:");
  theErrorMessage = theErrorMessage.replace("->","}  \\rightarrow \\text{");
  theErrorMessage = theErrorMessage.replace("?","}\\enspace " + latexErrorSign + " \\enspace  \\text{");
  theErrorMessage = "$$\\text{" + theErrorMessage.replace(/\n/g,"") + "}$$"
  #console.log "theErrorMessage: " + theErrorMessage
  return theErrorMessage

# there are around a dozen different unicodes that
# represent some sort of middle dot, let's catch the most
# common and turn them into what we can process
normaliseDots = (stringToNormalise) ->
  stringToNormalise = stringToNormalise.replace(new RegExp(String.fromCharCode(8901), 'g'), String.fromCharCode(dotprod_unicode));
  stringToNormalise = stringToNormalise.replace(new RegExp(String.fromCharCode(8226), 'g'), String.fromCharCode(dotprod_unicode));
  stringToNormalise = stringToNormalise.replace(new RegExp(String.fromCharCode(12539), 'g'), String.fromCharCode(dotprod_unicode));
  stringToNormalise = stringToNormalise.replace(new RegExp(String.fromCharCode(55296), 'g'), String.fromCharCode(dotprod_unicode));
  stringToNormalise = stringToNormalise.replace(new RegExp(String.fromCharCode(65381), 'g'), String.fromCharCode(dotprod_unicode));
  return stringToNormalise


TIMING_DEBUGS = false

run = (stringToBeRun, generateLatex = false) ->

  timeStart = new Date().getTime()

  #stringToBeRun = stringToBeRun + "\n"
  stringToBeRun = normaliseDots stringToBeRun

  #console.log "run running: " + stringToBeRun

  if stringToBeRun == "selftest"
    selftest()
    return

  #if (setjmp(stop_return))
  #  return

  if !inited
    inited = true
    init()

  i = 0
  n = 0
  indexOfPartRemainingToBeParsed = 0

  allReturnedPlainStrings = ""
  allReturnedLatexStrings = ""

  while (1)
    # while we can keep scanning commands out of the
    # passed input AND we can execute them...

    try
      errorMessage = ""
      check_stack()
      n = scan(stringToBeRun.substring(indexOfPartRemainingToBeParsed))
      p1 = pop()
      check_stack()
    catch error
      if PRINTOUTRESULT then console.log error
      #debugger
      allReturnedPlainStrings += error.message
      if generateLatex
        #debugger
        theErrorMessage = turnErrorMessageToLatex error.message
        allReturnedLatexStrings += theErrorMessage
      reset_after_error()

      break



    if (n == 0)
      break

    # if debug mode then print the source text

    #if (equaln(get_binding(symbol(TRACE)), 1)) {
    #  for (i = 0 i < n i++)
    #    if (s[i] != '\r')
    #      printchar(s[i])
    #  if (s[n - 1] != '\n') # n is not zero, see above
    #    printchar('\n')
    #}

    indexOfPartRemainingToBeParsed += n

    push(p1)
    #debugger
    errorWhileExecution = false
    try
      stringsEmittedByUserPrintouts = ""
      top_level_eval()
      #console.log "emitted string after top_level_eval(): >" + stringsEmittedByUserPrintouts + "<"
      #console.log "allReturnedPlainStrings string after top_level_eval(): >" + allReturnedPlainStrings + "<"

      p2 = pop()
      check_stack()

      if (isstr(p2))
        if DEBUG then console.log(p2.str)
        if DEBUG then console.log("\n")

      # if the return value is nil there isn't much point
      # in adding "nil" to the printout
      if (p2 == symbol(NIL))
        #collectedPlainResult = stringsEmittedByUserPrintouts
        collectedPlainResult = stringsEmittedByUserPrintouts
        if generateLatex
          collectedLatexResult = "$$" + stringsEmittedByUserPrintouts + "$$"
      else
        #console.log "emitted string before collectPlainStringFromReturnValue: >" + stringsEmittedByUserPrintouts + "<"
        #console.log "allReturnedPlainStrings string before collectPlainStringFromReturnValue: >" + allReturnedPlainStrings + "<"
        collectedPlainResult = print_expr(p2)
        collectedPlainResult += "\n"
        #console.log "collectedPlainResult: >" + collectedPlainResult + "<"
        if generateLatex
          collectedLatexResult = "$$" + collectLatexStringFromReturnValue(p2) + "$$"
          if DEBUG then console.log "collectedLatexResult: " + collectedLatexResult
      
      allReturnedPlainStrings += collectedPlainResult
      if generateLatex then allReturnedLatexStrings += collectedLatexResult

      if PRINTOUTRESULT
        if DEBUG then console.log "printline"
        if DEBUG then console.log collectedPlainResult
      #alert collectedPlainResult
      if PRINTOUTRESULT
        if DEBUG then console.log "display:"
        print2dascii(p2)

      if generateLatex then allReturnedLatexStrings += "\n"

    catch error
      errorWhileExecution = true
      collectedPlainResult = error.message
      if generateLatex then collectedLatexResult = turnErrorMessageToLatex error.message

      if PRINTOUTRESULT then console.log collectedPlainResult

      allReturnedPlainStrings += collectedPlainResult
      if collectedPlainResult != ""
        allReturnedPlainStrings += "\n"

      if generateLatex
        allReturnedLatexStrings += collectedLatexResult
        allReturnedLatexStrings += "\n"

      init()

  if allReturnedPlainStrings[allReturnedPlainStrings.length-1] == "\n"
    allReturnedPlainStrings = allReturnedPlainStrings.substring(0,allReturnedPlainStrings.length-1)

  if generateLatex
    if allReturnedLatexStrings[allReturnedLatexStrings.length-1] == "\n"
      allReturnedLatexStrings = allReturnedLatexStrings.substring(0,allReturnedLatexStrings.length-1)

  if generateLatex
    if DEBUG then console.log "allReturnedLatexStrings: " + allReturnedLatexStrings
    stringToBeReturned = [allReturnedPlainStrings, allReturnedLatexStrings]
  else
    stringToBeReturned = allReturnedPlainStrings

  if TIMING_DEBUGS
    timingDebugWrite = "run time on: " + stringToBeRun + " : " + (new Date().getTime() - timeStart) + "ms"
    console.log timingDebugWrite

  allReturnedPlainStrings = ""
  allReturnedLatexStrings = ""
  return stringToBeReturned

check_stack = ->
  if (tos != 0)
    debugger
    stop("stack error")
  if (frame != TOS)
    debugger
    stop("frame error")
  if chainOfUserSymbolsNotFunctionsBeingEvaluated.length != 0
    debugger
    stop("symbols evaluation still ongoing?")
  if evaluatingAsFloats != 0
    debugger
    stop("numeric evaluation still ongoing?")
  if evaluatingPolar != 0
    debugger
    stop("evaluation of polar still ongoing?")

# cannot reference symbols yet

# returns nil on stack if no result to print

top_level_eval = ->
  if DEBUG then console.log "#### top level eval"

  trigmode = 0

  shouldAutoexpand = symbol(AUTOEXPAND)

  if (isZeroAtomOrTensor(get_binding(shouldAutoexpand)))
    expanding = 0
  else
    expanding = 1

  originalArgument = top()
  Eval()
  evalledArgument = top()

  # "draw", "for" and "setq" return "nil", there is no result to print
  if (evalledArgument == symbol(NIL))
    return

  # update "last" to contain the last result
  set_binding(symbol(LAST), evalledArgument)

  if (!isZeroAtomOrTensor(get_binding(symbol(BAKE))))
    bake()
    evalledArgument = top()

  # If user asked explicitly asked to evaluate "i" or "j" and
  # they represent the imaginary unit (-1)^(1/2), then 
  # show (-1)^(1/2).
  if ((originalArgument == symbol(SYMBOL_I) || originalArgument == symbol(SYMBOL_J)) && isimaginaryunit(evalledArgument))
    return
  # In all other cases, replace all instances of (-1)^(1/2) in the result
  # with the symbol "i" or "j" depending on which one
  # represents the imaginary unit
  else if (isimaginaryunit(get_binding(symbol(SYMBOL_J))))
    push(imaginaryunit)
    push_symbol(SYMBOL_J)
    subst()
  else if (isimaginaryunit(get_binding(symbol(SYMBOL_I))))
    push(imaginaryunit)
    push_symbol(SYMBOL_I)
    subst()


check_esc_flag = ->
  if (esc_flag)
    stop("esc key")

# this is called when the whole notebook is re-run
# so we get the chance of clearing the whole state from
# scratch.
# In practice, the state we need to clear that persists
# across blocks are only the patterns, so
# just eject those.
clearAlgebraEnvironment = ->
  #console.log "CLEARING clearAlgebraEnvironment ============================================================="
  do_clearall()

computeDependenciesFromAlgebra = (codeFromAlgebraBlock) ->
  if DEBUG then console.log "computeDependenciesFromAlgebra!!!"
  # return findDependenciesInScript(codeFromAlgebraBlock, true)[6]

  # TODO this part below is duplicated from computeResultsAndJavaScriptFromAlgebra
  #      ...should refactor.
  originalcodeFromAlgebraBlock = codeFromAlgebraBlock
  keepState = true
  called_from_Algebra_block = true

  #console.log "codeFromAlgebraBlock: " + codeFromAlgebraBlock

  codeFromAlgebraBlock = normaliseDots codeFromAlgebraBlock

  if !keepState
    userSimplificationsInListForm = []
    userSimplificationsInProgramForm = ""
    for i in userSimplificationsInListForm
      #console.log "silentpattern(" + car(i) + ","+cdr(i)+")"
      userSimplificationsInProgramForm += "silentpattern(" + car(i) + ","+ car(cdr(i)) + "," + car(cdr(cdr(i))) + ")\n"

    do_clearall()
    codeFromAlgebraBlock = userSimplificationsInProgramForm + codeFromAlgebraBlock
    if DEBUG then console.log "codeFromAlgebraBlock including patterns: " + codeFromAlgebraBlock

  if DEBUG
    console.log "computeDependenciesFromAlgebra: patterns in the list --------------- "
    for i in userSimplificationsInListForm
      console.log car(i) + ","+cdr(i)+")"
    console.log "...end of list --------------- "


  called_from_Algebra_block = false

  return findDependenciesInScript(codeFromAlgebraBlock, true)[6]

computeResultsAndJavaScriptFromAlgebra = (codeFromAlgebraBlock) ->


  originalcodeFromAlgebraBlock = codeFromAlgebraBlock
  keepState = true
  called_from_Algebra_block = true

  timeStartFromAlgebra  = new Date().getTime()

  if TIMING_DEBUGS
    console.log " --------- computeResultsAndJavaScriptFromAlgebra input: " + codeFromAlgebraBlock + " at: " + (new Date())

  # we start "clean" each time:
  # clear all the symbols and then re-define
  # the "starting" symbols.
  
  #console.log "codeFromAlgebraBlock: " + codeFromAlgebraBlock

  codeFromAlgebraBlock = normaliseDots codeFromAlgebraBlock



  stringToBeRun = codeFromAlgebraBlock

  if DEBUG
    console.log "computeResultsAndJavaScriptFromAlgebra: patterns in the list --------------- "
    for i in userSimplificationsInListForm
      console.log car(i) + ","+cdr(i)+")"
    console.log "...end of list --------------- "

  if !keepState
    userSimplificationsInListForm = []
    userSimplificationsInProgramForm = ""
    for i in userSimplificationsInListForm
      #console.log "silentpattern(" + car(i) + ","+cdr(i)+")"
      userSimplificationsInProgramForm += "silentpattern(" + car(i) + ","+ car(cdr(i)) + "," + car(cdr(cdr(i))) + ")\n"

    do_clearall()
    codeFromAlgebraBlock = userSimplificationsInProgramForm + codeFromAlgebraBlock
    if DEBUG then console.log "codeFromAlgebraBlock including patterns: " + codeFromAlgebraBlock

  #debugger
  [testableStringIsIgnoredHere,result,code,readableSummaryOfCode, latexResult, errorMessage, dependencyInfo] =
    findDependenciesInScript(codeFromAlgebraBlock)

  called_from_Algebra_block = false

  if readableSummaryOfCode != "" or errorMessage != ""
    result += "\n" + readableSummaryOfCode
    if errorMessage != ""
      result += "\n" + errorMessage
    result = result.replace /\n/g,"\n\n"

    latexResult += "\n" + "$$" + readableSummaryOfCode + "$$"
    if errorMessage != ""
      latexResult += turnErrorMessageToLatex  errorMessage
    latexResult = latexResult.replace /\n/g,"\n\n"

  # remove empty results altogether from latex output, which happens
  # for example for assignments to variables or
  # functions definitions
  latexResult = latexResult.replace /\n*/,""
  latexResult = latexResult.replace /\$\$\$\$\n*/g,""

  code = code.replace /Math\./g,""
  code = code.replace /\n/g,"\n\n"

  #console.log "code: " + code
  #console.log "result: " + result
  #console.log "latexResult: " + latexResult

  if TIMING_DEBUGS
    console.log "computeResultsAndJavaScriptFromAlgebra time (total time from notebook and back) for: " + stringToBeRun + " : "+ ((new Date().getTime()) - timeStartFromAlgebra) + "ms"

  #code: "// no code generated yet\n//try again later"
  #code: "console.log('some passed code is run'); window.something = 1;"
  code: code

  # TODO temporarily pass latex in place of standard result too
  result: latexResult
  latexResult: latexResult
  dependencyInfo: dependencyInfo

(exports ? this).run = run
(exports ? this).findDependenciesInScript = findDependenciesInScript
(exports ? this).computeDependenciesFromAlgebra = computeDependenciesFromAlgebra
(exports ? this).computeResultsAndJavaScriptFromAlgebra = computeResultsAndJavaScriptFromAlgebra
(exports ? this).clearAlgebraEnvironment = clearAlgebraEnvironment
