public JST.Identifier ApplyId(JST.Identifier id) { var e = default(Expression); if (subst.TryGetValue(id, out e)) { var r = e as ReadExpression; if (r != null) { var cell = r.Address.IsAddressOfCell; if (cell != null) { var id2 = cell.IsVariable; if (id2 != null) { return(id2); } // else: fall-through } // else: fall-through } // else: fall-through } // else: fall-through return(id); }
public MethodCompiler(TypeDefinitionCompiler parent, JST.NameSupply outerNameSupply, CST.MethodDef methodDef, MethodCompilationMode mode) { env = parent.Env; this.parent = parent; methEnv = parent.TyconEnv.AddSelfTypeBoundArguments().AddMethod(methodDef).AddSelfMethodBoundArguments(); messageCtxt = CST.MessageContextBuilders.Env(methEnv); this.mode = mode; this.outerNameSupply = outerNameSupply; var common = default(JST.NameSupply); switch (mode) { case MethodCompilationMode.SelfContained: common = outerNameSupply; // Will be bound by function passed to root's BindMethod rootId = common.GenSym(); assemblyId = common.GenSym(); typeDefinitionId = common.GenSym(); break; case MethodCompilationMode.DirectBind: common = outerNameSupply.Fork(); // Already bound rootId = parent.RootId; assemblyId = parent.AssemblyId; typeDefinitionId = parent.TypeDefinitionId; break; default: throw new ArgumentOutOfRangeException("mode"); } nameSupply = common.Fork(); simpNameSupply = common.Fork(); }
public Variable(JST.Identifier id, ArgLocal argLocal, bool isInit, bool isReadOnly, CST.TypeRef type) { Id = id; ArgLocal = argLocal; IsInit = isInit; IsReadOnly = isReadOnly; Type = type; }
public JST.Identifier FreshenArgument(JST.Identifier id, TypeRef type) { var newid = NameSupply.GenSym(); var cell = new VariableCell(newid); Bind(id, cell.Read()); CompEnv.AddVariable(newid, ArgLocal.Local, true, true, type); return(newid); }
public BBLoop(BasicBlock head, BasicBlock tail, IMSet<BasicBlock> body, JST.Identifier label) { Head = head; Tail = tail; Body = body; Label = label; var headEscapes = false; var headbranchbb = head as BranchBasicBlock; foreach (var t in head.Targets) { if (!body.Contains(t)) headEscapes = true; } var tailEscapes = false; var tailbranchbb = tail as BranchBasicBlock; foreach (var t in tail.Targets) { if (!body.Contains(t)) tailEscapes = true; } if (!headEscapes && tailEscapes && tailbranchbb != null) { if (tailbranchbb.Target.Equals(head)) Flavor = LoopFlavor.DoWhile; else if (tailbranchbb.Fallthrough.Equals(head)) Flavor = LoopFlavor.FlippedDoWhile; else throw new InvalidOperationException("invalid loop"); } else if (headEscapes && !tailEscapes && headbranchbb != null) { if (body.Contains(headbranchbb.Target)) Flavor = LoopFlavor.WhileDo; else if (body.Contains(headbranchbb.Fallthrough)) Flavor = LoopFlavor.FlippedWhileDo; else throw new InvalidOperationException("invalid loop"); } else if (!headEscapes && !tailEscapes) Flavor = LoopFlavor.Loop; else if (headEscapes && tailEscapes && headbranchbb != null && tailbranchbb != null) { // Could encode as do-while with a break at start, or while-do with a break at end. if (body.Contains(headbranchbb.Target)) Flavor = LoopFlavor.WhileDo; else if (body.Contains(headbranchbb.Fallthrough)) Flavor = LoopFlavor.FlippedWhileDo; else throw new InvalidOperationException("invalid loop"); } else Flavor = LoopFlavor.Unknown; }
protected void Bind(JST.Identifier id, Expression e) { if (subst.ContainsKey(id)) { subst[id] = e; } else { subst.Add(id, e); } }
public Expression ApplyReadFrom(JST.Identifier id) { var e = default(Expression); if (subst.TryGetValue(id, out e)) { return(e); } else { return(new VariableCell(id).Read()); } }
public Cell ApplyCell(JST.Identifier id) { var e = default(Expression); if (subst.TryGetValue(id, out e)) { var r = e as ReadExpression; if (r != null) { var cell = r.Address.IsAddressOfCell; if (cell != null) { return(cell); } // else: fall-through } // else: fall-through } // else: fall-through return(new VariableCell(id)); }
public void BindArgument(JST.Identifier id, Expression argument) { Bind(id, argument); }
private void EnsurePathExists(ISeq<JST.Statement> statements, JST.Expression script, bool isStatic) { var path = JST.Expression.ExplodePath(script); for (var i = isStatic ? 0 : 1; i < path.Count - 1; i++) { var prefixPath = new Seq<JST.PropertyName>(); for (var j = 0; j <= i; j++) prefixPath.Add(path[j]); var prefix = JST.Expression.Path(prefixPath); if (i == 0) { var exId = new JST.Identifier("e"); #if !JSCRIPT_IS_CORRECT statements.Add(JST.Statement.Var(exId)); #endif statements.Add (new JST.TryStatement (new JST.Statements(new JST.ExpressionStatement(prefix)), new JST.CatchClause(exId, new JST.Statements(JST.Statement.Assignment(prefix, new JST.ObjectLiteral()))))); } else if (!path[i].Value.Equals(Constants.prototype.Value, StringComparison.Ordinal)) statements.Add (new JST.IfStatement (JST.Expression.IsNull(prefix), new JST.Statements(JST.Statement.Assignment(prefix, new JST.ObjectLiteral())))); } }
public readonly JST.Identifier StateId; // temporary holding machine state public StatePCPseudoCell(JST.Identifier stateId) { StateId = stateId; }
public LoopCandidateBasicBlock(int id, JST.Identifier label, MachineState initialState) : base(id, new Instructions(initialState)) { Label = label; }
private JST.Statement WithLineCounts(JST.Statement statement, Func<int> nextLine, int currDepth, Set<JST.Identifier> lineCountIds) { if (statement.Flavor == JST.StatementFlavor.Try) { var trys = (JST.TryStatement)statement; if (trys.Catch != null) { var tryBody = WithLineCounts(trys.Body, nextLine, currDepth + 1, lineCountIds); var catchBody = new Seq<JST.Statement>(); var saveid = new JST.Identifier(Constants.DebugCurrentLine.Value + "_" + currDepth); lineCountIds.Add(saveid); catchBody.Add(JST.Statement.Assignment(saveid.ToE(), Constants.DebugCurrentLine.ToE())); foreach (var s in WithLineCounts(trys.Catch.Body, nextLine, currDepth + 1, lineCountIds).Body) catchBody.Add(s); var catchClause = new JST.CatchClause(trys.Catch.Loc, trys.Catch.Name, new JST.Statements(catchBody)); var finallyClause = default(JST.FinallyClause); if (trys.Finally != null) finallyClause = new JST.FinallyClause (trys.Finally.Loc, WithLineCounts(trys.Finally.Body, nextLine, currDepth + 1, lineCountIds)); return new JST.TryStatement(trys.Loc, tryBody, catchClause, finallyClause); } // else: fall-through } // else: fall-through return statement.CloneWithSubStatementss (statement.SubStatementss.Select(ss => WithLineCounts(ss, nextLine, currDepth, lineCountIds)).ToSeq()); }
public void Bind(Identifier id) { hidden.Add(id); }
public bool IsHidden(Identifier id) { return(hidden.Contains(id)); }
public BBLoop(BasicBlock head, BasicBlock tail, IMSet <BasicBlock> body, JST.Identifier label) { Head = head; Tail = tail; Body = body; Label = label; var headEscapes = false; var headbranchbb = head as BranchBasicBlock; foreach (var t in head.Targets) { if (!body.Contains(t)) { headEscapes = true; } } var tailEscapes = false; var tailbranchbb = tail as BranchBasicBlock; foreach (var t in tail.Targets) { if (!body.Contains(t)) { tailEscapes = true; } } if (!headEscapes && tailEscapes && tailbranchbb != null) { if (tailbranchbb.Target.Equals(head)) { Flavor = LoopFlavor.DoWhile; } else if (tailbranchbb.Fallthrough.Equals(head)) { Flavor = LoopFlavor.FlippedDoWhile; } else { throw new InvalidOperationException("invalid loop"); } } else if (headEscapes && !tailEscapes && headbranchbb != null) { if (body.Contains(headbranchbb.Target)) { Flavor = LoopFlavor.WhileDo; } else if (body.Contains(headbranchbb.Fallthrough)) { Flavor = LoopFlavor.FlippedWhileDo; } else { throw new InvalidOperationException("invalid loop"); } } else if (!headEscapes && !tailEscapes) { Flavor = LoopFlavor.Loop; } else if (headEscapes && tailEscapes && headbranchbb != null && tailbranchbb != null) { // Could encode as do-while with a break at start, or while-do with a break at end. if (body.Contains(headbranchbb.Target)) { Flavor = LoopFlavor.WhileDo; } else if (body.Contains(headbranchbb.Fallthrough)) { Flavor = LoopFlavor.FlippedWhileDo; } else { throw new InvalidOperationException("invalid loop"); } } else { Flavor = LoopFlavor.Unknown; } }
public void SeenVariablePointer(JST.Identifier id, bool isAlwaysUsed) { Add(VariablePointers, id, 1, isAlwaysUsed); }
public VariableCell(JST.Identifier id) { Id = id; }