aa
HM3.java
Go to the documentation of this file.
1 package com.cliffc.aa.HM;
2 
3 import com.cliffc.aa.type.*;
4 import com.cliffc.aa.util.*;
5 import org.jetbrains.annotations.NotNull;
6 
7 import java.util.*;
8 
9 // Hindley-Milner typing. Complete stand-alone, for research. MEETs base
10 // types, instead of declaring type error. Requires SSA renumbering; uses a
11 // global Env instead locally tracking.
12 //
13 // Testing in this version changing out the AST tree-walk for a worklist based
14 // approach, where unification happens in any order. In particular, it means
15 // that (unlike a tree-walk), function types will get used before the function
16 // is typed. This means that a "fresh" copy of a function type to be used to
17 // unify against will not have all the contraints at first unification.
18 //
19 // (0) Build the AST with parent pointers also, and declare the AST a "graph".
20 // Break the HM() call into a "makes progress" test and a "do it".
21 // (1) Find all ids (which are all unique ala SSA), and keep a stack of the
22 // non-generative ones at each Ident. Leaf AST on the worklist. Check for
23 // missing-name syntax. Requires 1 tree pass.
24 // (2) Put root on worklist.
25 // (3) Pull from worklist until empty:
26 // (4) Call hm() to get a HMType or null.
27 // (6) If progress (not null)
28 // (7) Then set new HMType, and put graph neighbors on worklist
29 // (8) Report HMTypes.
30 //
31 public class HM3 {
32  static final HashMap<String,HMType> ENV = new HashMap<>();
33 
34  public static HMType hm( Syntax prog) {
35  // Simple types
36  HMVar bool = new HMVar(TypeInt.BOOL);
37  HMVar int64 = new HMVar(TypeInt.INT64);
38  HMVar flt64 = new HMVar(TypeFlt.FLT64);
39  HMVar strp = new HMVar(TypeMemPtr.STRPTR);
40 
41  // Primitives
42  HMVar var1 = new HMVar();
43  HMVar var2 = new HMVar();
44  ENV.put("pair",Oper.fun(var1, Oper.fun(var2, new Oper("pair",var1,var2))));
45 
46  // { pred:bool lhs:var3 rhs:var3 -> var3 }
47  HMVar var3 = new HMVar();
48  ENV.put("if/else",Oper.fun(bool,Oper.fun(var3,Oper.fun(var3,var3))));
49 
50  ENV.put("dec",Oper.fun(int64,int64));
51  ENV.put("*",Oper.fun(int64,Oper.fun(int64,int64)));
52  ENV.put("==0",Oper.fun(int64,bool));
53 
54  // Print a string; int->str
55  ENV.put("str",Oper.fun(int64,strp));
56  // Factor
57  ENV.put("factor",Oper.fun(flt64,new Oper("pair",flt64,flt64)));
58 
59 
60  // Prep for SSA: pre-gather all the (unique) ids. Store a linked-list of
61  // non-generative IDs (those mid-definition in Lambda & Let, or in the old
62  // "nongen" HashSet), for use by Ident.hm.
63  final Worklist work = new Worklist();
64  prog.get_ids(null,work);
65 
66  // Worklist:
67  int cnt=0;
68  while( work.len()>0 ) { // While not empty
69  Syntax s = work.pop(); // Get work
70  HMType nnn = s.hm(work);
71  if( nnn!=null ) { // If progress
72  s._hm = nnn; // Move progress state
73  s.add_neighbors(work); // Neighbors get reinspected for progress
74  }
75  assert prog.check_progress(work); // Everything that can make progress is on the worklist
76  cnt++; // Which iter count, for debug only
77  }
78  return prog._hm;
79  }
80  static void reset() { ENV.clear(); HMType.reset(); }
81 
82  // Small classic tree of HMVars, immutable, with sharing at the root parts.
83  static class VStack implements Iterable<HMVar> {
84  final VStack _par;
85  final HMVar _nongen;
86  VStack( VStack par, HMVar nongen ) { _par=par; _nongen=nongen; }
87  @Override public String toString() { return str(new SB()).toString(); }
88  SB str(SB sb) {
89  _nongen._str(sb,new VBitSet(),false);
90  if( _par!=null ) _par.str(sb.p(" >> "));
91  return sb;
92  }
93  @NotNull @Override public Iterator<HMVar> iterator() { return new Iter(); }
94  private class Iter implements Iterator<HMVar> {
95  private VStack _vstk;
96  Iter() { _vstk=VStack.this; }
97  @Override public boolean hasNext() { return _vstk!=null; }
98  @Override public HMVar next() { HMVar v = _vstk._nongen; _vstk = _vstk._par; return v; }
99  }
100  }
101 
102  // Worklist of Syntax nodes
103  private static class Worklist {
104  private final Ary<Syntax> _ary = new Ary<>(Syntax.class); // For picking random element
105  private final HashSet<Syntax> _work = new HashSet<>(); // For preventing dups
106  public int len() { return _ary.len(); }
107  public void push(Syntax s) { if( !_work.contains(s) ) _work.add(_ary.push(s)); }
108  public Syntax pop() { Syntax s = _ary.pop(); _work.remove(s); return s; }
109  public boolean has(Syntax s) { return _work.contains(s); }
110  public void addAll(Ary<? extends Syntax> ss) { for( Syntax s : ss ) push(s); }
111  @Override public String toString() { return _ary.toString(); }
112  }
113 
114  // Program Abstract Syntax Tree
115  static abstract class Syntax {
116  Syntax _par; // Parent in the AST.
117  Syntax[] _kids; // Children in the AST.
118  HMType _hm; // The Hindley-Milner type
119  // Find the H-M type for this node, strictly by looking at the children H-M
120  // type and adding any constraints.
121  abstract HMType hm(Worklist work); // Hindley-Milner effect for this AST node
122  // Prep call: gather unique IDs and find/set the non-gen IDs for this AST
123  // node and subtree.
124  abstract void get_ids(VStack vstk, Worklist work);
125  // Add self to the worklist, IFF kids have already computed an initial H-M type.
126  protected final void add_work(Worklist work) { if( all_kids_ready() ) work.push(this); }
127  // Add neighbors (kids, parent) and NOT self to the worklist.
128  final void add_neighbors(Worklist work) {
129  if( _par!=null ) _par.add_work(work);
130  if( _kids!=null )
131  for( Syntax kid : _kids )
132  kid.add_work(work);
133  }
134  // Child classes inspect their kids
135  final boolean all_kids_ready() {
136  if( _kids==null ) return true;
137  for( Syntax kid : _kids ) if( kid._hm==null ) return false;
138  return true;
139  }
140  // Progress if _hm is not null, and a call to hm() either returns something
141  // not 'eq' to _hm or unifies with anything.
142  abstract boolean progress();
143  // Check that every node which can make progress is on the worklist
144  boolean check_progress(Worklist work) {
145  if( all_kids_ready() ) // If kids are not ready, then cannot compute hm() so not on worklist
146  if( _hm==null || progress() ) // Progress is possible
147  if( !work.has(this) ) // Not on worklist?
148  return false; // Fails check
149  if( _kids!=null ) // For all kids
150  for( Syntax kid : _kids )
151  if( !kid.check_progress(work) ) // Recursively check nodes that can make progress on worklist
152  return false;
153  return true;
154  }
155  }
156  public static class Con extends Syntax {
157  final Type _t;
158  Con(Type t) { _t=t; }
159  @Override public String toString() { return _t.toString(); }
160  @Override HMType hm(Worklist work) { return _hm==null ? new HMVar(_t) : null; }
161  @Override boolean progress() { return false; }
162  @Override void get_ids(VStack vstk,Worklist work) { add_work(work); }
163  }
164 
165  public static class Ident extends Syntax {
166  final String _name;
168  Ident(String name) { _name=name; }
169  @Override public String toString() { return _name; }
170  @Override HMType hm(Worklist work) {
171  if( _hm!=null ) return null;
172  HMType t = ENV.get(_name).find();
173  return t.fresh(_vstk);
174  }
175  // Progress if named HMType unioned into, and thus both put on the worklist
176  // and has its _hm field cleared to signal a need for a fresh() copy.
177  @Override boolean progress() { return false; }
178  @Override void get_ids(VStack vstk,Worklist work) {
179  HMType t = ENV.get(_name);
180  if( t==null )
181  throw new RuntimeException("Parse error, "+_name+" is undefined");
182  if( t._ids==null ) t._ids = new Ary<>(Ident.class);
183  t._ids.push(this);
184  _vstk=vstk;
185  add_work(work);
186  }
187  }
188 
189  public static class Lambda extends Syntax {
190  final String _arg0;
191  Lambda(String arg0, Syntax body) { _kids=new Syntax[]{body}; body._par=this; _arg0=arg0; }
192  private Syntax body() { return _kids[0]; }
193  @Override public String toString() { return "{ "+_arg0+" -> "+body()+" }"; }
194  @Override HMType hm(Worklist work) {
195  if( _hm!=null && !progress() ) return null;
196  HMType tnew = ENV.get(_arg0).find();
197  HMType trez = body()._hm.find();
198  return Oper.fun(tnew,trez);
199  }
200  @Override boolean progress() {
201  HMType tnew = ENV.get(_arg0).find();
202  HMType trez = body()._hm.find();
203  // Progress if _hm is NOT a Oper.fun, OR
204  // !_hm[0].eq(tnew) || _hm[1].eq(trez);
205  if( !(_hm instanceof Oper) ) return true;
206  if( !((Oper)_hm)._name.equals("->") ) return true;
207  HMType fcn = ((Oper)_hm)._args[0].find();
208  HMType rez = ((Oper)_hm)._args[1].find();
209  return !fcn.eq(tnew) || !rez.eq(trez);
210  }
211  @Override void get_ids(VStack vstk,Worklist work) {
212  HMVar var = new HMVar();
213  ENV.put(_arg0, var);
214  body().get_ids(new VStack(vstk,var),work);
215  }
216  }
217  public static class Let extends Syntax {
218  final String _arg0;
219  Let(String arg0, Syntax body, Syntax use) { _arg0=arg0; _kids=new Syntax[]{body,use}; body._par=use._par=this; }
220  private Syntax body() { return _kids[0]; }
221  private Syntax use () { return _kids[1]; }
222  @Override public String toString() { return "let "+_arg0+" = "+body()+" in "+use()+" }"; }
223  @Override HMType hm(Worklist work) {
224  if( _hm!=null && !progress() ) return null;
225  HMType tbody = body()._hm.find();
226  HMType trez = use() ._hm.find();
227  HMType tnew = ENV.get(_arg0).find();
228  tnew.union(tbody,work);
229  if( _hm!=null ) _hm.union(trez,work);
230  return trez;
231  }
232  @Override boolean progress() {
233  HMType tbody = body()._hm.find();
234  HMType trez = use() ._hm.find();
235  HMType tnew = ENV.get(_arg0).find();
236  // Progress if tnew != tbody (they get unioned) OR
237  // trez != _hm
238  return !tnew.eq(tbody) || !_hm.find().eq(trez);
239  }
240  @Override void get_ids(VStack vstk,Worklist work) {
241  HMVar var = new HMVar();
242  ENV.put(_arg0, var);
243  body().get_ids(new VStack(vstk,var),work);
244  use() .get_ids(vstk,work);
245  }
246  }
247  public static class Apply extends Syntax {
249  private Syntax fun() { return _kids[0]; }
250  private Syntax arg() { return _kids[1]; }
251  @Override public String toString() { return "("+fun()+" "+arg()+")"; }
252  @Override HMType hm(Worklist work) {
253  if( _hm!=null && !progress() ) return null;
254  HMType tfun = fun()._hm.find();
255  HMType targ = arg()._hm.find();
256  HMType trez = new HMVar();
257  HMType nfun = Oper.fun(targ,trez);
258  nfun.union(tfun,work);
259  if( _hm!=null ) _hm.union(trez.find(),work);
260  return trez.find();
261  }
262  @Override boolean progress() {
263  // Progress if tfun is not a Oper.fun, OR
264  // tfun[0] != targ (they get unioned)
265  HMType tfun = fun()._hm.find();
266  HMType targ = arg()._hm.find();
267  if( !(tfun instanceof Oper) ) return true;
268  if( !((Oper)tfun)._name.equals("->") ) return true;
269  HMType arg0 = ((Oper)tfun)._args[0].find();
270  return !arg0.eq(targ);
271  }
272  @Override void get_ids(VStack vstk,Worklist work) { fun().get_ids(vstk,work); arg().get_ids(vstk,work); }
273  }
274 
275 
276 
277  public static abstract class HMType {
278  HMType _u; // U-F; always null for Oper
279  final int _uid;
280  private static int CNT;
281  static void reset() { CNT=1; }
282  HMType() { _uid=CNT++; }
283  Ary<Ident> _ids; // Progress for IDs when types change
284  abstract HMType union(HMType t, Worklist work);
285  abstract HMType find();
286  @Override public final String toString() { return _str(new SB(),new VBitSet(),true).toString(); }
287  public String str() { return _str(new SB(),new VBitSet(),false).toString(); }
288  abstract SB _str(SB sb, VBitSet vbs, boolean debug);
289  boolean is_top() { return _u==null; }
290  static final HashMap<HMVar,HMVar> EQS = new HashMap<>();
291  final boolean eq( HMType v ) { EQS.clear(); return find()._eq(v, new BitSetSparse()); }
292  abstract boolean _eq( HMType v, BitSetSparse dups );
293 
295  HashMap<HMVar,HMVar> vars = new HashMap<>();
296  HashMap<Oper,Oper> opers = new HashMap<>();
297  return find()._fresh(vstk,vars,opers);
298  }
299  abstract HMType _fresh(VStack vstk, HashMap<HMVar,HMVar> vars, HashMap<Oper,Oper> opers);
300 
301  boolean occurs_in(VStack vstk, VBitSet dups) {
302  if( vstk==null ) return false;
303  for( HMVar x : vstk ) if( occurs_in_type(x,dups) ) return true;
304  return false;
305  }
306  boolean occurs_in(HMType[] args, VBitSet dups) {
307  for( HMType x : args ) if( occurs_in_type(x,dups) ) return true;
308  return false;
309  }
310  boolean occurs_in_type(HMType v, VBitSet dups) {
311  assert is_top();
312  if( dups.tset(v._uid) )
313  return false; // Been there, done that
314  HMType y = v.find(); // Find top
315  if( y==this ) // Occurs in type?
316  return true; // Yup, occurs in type right here
317  if( y instanceof Oper ) // Structural recursive test
318  return occurs_in(((Oper)y)._args,dups);
319  return false;
320  }
321  }
322 
323  static class HMVar extends HMType {
324  private Type _t;
325  HMVar() { this(Type.ANY); }
326  HMVar(Type t) { _t=t; }
327  public Type type() { assert is_top(); return _t; }
328  @Override public SB _str(SB sb, VBitSet dups, boolean debug) {
329  if( _u!=null && !debug ) return _u._str(sb,dups,debug); // Clean print; skip to U-F root & print
330  sb.p("v").p(_uid);
331  if( dups.tset(_uid) ) return sb.p("$"); // Stop infinite print loops
332  if( _t!=Type.ANY ) _t.str(sb.p(":"),dups,null,false);
333  if( _u!=null ) _u._str(sb.p(">>"),dups,debug);
334  return sb;
335  }
336 
337  @Override HMType find() {
338  HMType u = _u;
339  if( u==null ) return this; // Top of union tree
340  if( u._u==null ) return u; // One-step from top
341  // Classic U-F rollup
342  while( u._u!=null ) u = u._u; // Find the top
343  HMType x = this; // Collapse all to top
344  while( x._u!=u ) { HMType tmp = x._u; x._u=u; x=tmp;}
345  return u;
346  }
347  @Override HMType union(HMType that, Worklist work) {
348  if( _u!=null ) return find().union(that,work);
349  if( that instanceof HMVar ) that = that.find();
350  if( this==that ) return this; // Do nothing
351  if( occurs_in_type(that, new VBitSet()) )
352  //throw new RuntimeException("recursive unification");
353  System.out.println("recursive unification");
354 
355  if( that instanceof HMVar ) {
356  HMVar v2 = (HMVar)that;
357  // Order, so keep smaller _uids by default
358  if( _uid < v2._uid ) return that.union(this,work);
359  v2._t = _t.meet(v2._t); // Lattice MEET instead of unification failure
360  }
361  else if( _t!=Type.ANY ) // Else this var is un-MEETd with any Con
362  throw new RuntimeException("Cannot unify "+this+" and "+that);
363  if( _ids!=null ) { // Move this ids into that ids
364  if( that._ids==null ) that._ids = _ids;
365  else that._ids.addAll(_ids);
366  _ids=null; // No longer here
367  }
368  if( that._ids!=null ) { // All that ids onto worklist
369  for( Ident id : that._ids ) id._hm=null; // Flag as 1-shot re-freshen
370  work.addAll(that._ids); // On to worklist
371  }
372  return _u = that; // Classic U-F union this into that.
373  }
374 
375  @Override boolean _eq( HMType v, BitSetSparse dups ) {
376  if( this==v ) return true;
377  if( v==null ) return false;
378  HMType v2 = v.find();
379  if( !(v2 instanceof HMVar) ) return false;
380  assert _u==null && v2._u==null;
381  if( _t != ((HMVar)v2)._t) return false;
382  HMVar v3 = EQS.computeIfAbsent(this,k -> (HMVar)v2);
383  return v2 == v3;
384  }
385 
386  @Override HMType _fresh(VStack vstk, HashMap<HMVar,HMVar> vars, HashMap<Oper,Oper> opers) {
387  assert is_top();
388  return occurs_in(vstk, new VBitSet()) // If in the lexical Stack
389  ? this // Keep same var
390  : vars.computeIfAbsent(this, e -> new HMVar(_t));
391  }
392  }
393 
394  static class Oper extends HMType {
395  final String _name;
396  final HMType[] _args;
397  Oper(String name, HMType... args) { _name=name; _args=args; }
398  static Oper fun(HMType... args) { return new Oper("->",args); }
399  @Override public SB _str(SB sb, VBitSet dups, boolean debug) {
400  if( dups.tset(_uid) ) return sb.p("v").p(_uid).p("$"); // Stop infinite print loops
401  if( _name.equals("->") ) {
402  if( debug ) sb.p("v").p(_uid).p(":");
403  sb.p("{ ");
404  _args[0]._str(sb,dups,debug);
405  sb.p(" -> ");
406  _args[1]._str(sb,dups,debug);
407  return sb.p(" }");
408  }
409  sb.p(_name);
410  if( debug ) sb.p(_uid);
411  sb.p('(');
412  for( HMType t : _args )
413  t._str(sb,dups,debug).p(',');
414  return sb.unchar().p(')');
415  }
416 
417  @Override HMType find() { return this; }
418  @Override HMType union(HMType that, Worklist work) {
419  if( this==that ) return this;
420  if( !(that instanceof Oper) ) return that.union(this,work);
421  if( _uid < that._uid ) return that.union(this,work); // Minimize unique CNT values
422  Oper op2 = (Oper)that;
423  if( !_name.equals(op2._name) ||
424  _args.length != op2._args.length )
425  throw new RuntimeException("Cannot unify "+this+" and "+that);
426  for( int i=0; i<_args.length; i++ )
427  _args[i] = _args[i].union(op2._args[i],work); // Both union, and update U-F
428  if( _ids!=null ) { for( Ident id : _ids ) id._hm=null; work.addAll( _ids); }
429  if( that._ids!=null ) { for( Ident id : that._ids ) id._hm=null; work.addAll(that._ids); }
430  return that;
431  }
432  @Override boolean _eq( HMType v, BitSetSparse dups ) {
433  assert is_top() && v.is_top();
434  if( this==v ) return true;
435  if( !(v instanceof Oper) ) return false;
436  if( dups.tset(_uid,v._uid) )
437  return true; // Checked already, something else has to be equal/unequal
438  Oper o = (Oper)v;
439  if( !_name.equals(o._name) ||
440  _args.length!=o._args.length ) return false;
441  for( int i=0; i<_args.length; i++ ) {
442  HMType h0 = _args[i];
443  HMType h1 = o._args[i];
444  if( !h0.is_top() ) _args[i] = h0 = h0.find();
445  if( !h1.is_top() ) o._args[i] = h1 = h1.find();
446  if( !h0._eq(h1,dups) )
447  return false;
448  }
449  return true;
450  }
451  @Override HMType _fresh(VStack vstk, HashMap<HMVar,HMVar> vars, HashMap<Oper,Oper> opers) {
452  assert is_top();
453  Oper op = opers.get(this);
454  if( op!=null ) return op;
455  HMType[] args = new HMType[_args.length];
456  op = new Oper(_name,args);
457  opers.put(this,op); // Stop cyclic structure endless looping
458  for( int i=0; i<_args.length; i++ )
459  args[i] = _args[i].find()._fresh(vstk,vars,opers);
460  return op;
461  }
462 
463  }
464 }
com.cliffc.aa.HM.HM3.Lambda._arg0
final String _arg0
Definition: HM3.java:190
com.cliffc.aa.HM.HM3.Worklist.has
boolean has(Syntax s)
Definition: HM3.java:109
com.cliffc.aa.HM.HM3.Oper._fresh
HMType _fresh(VStack vstk, HashMap< HMVar, HMVar > vars, HashMap< Oper, Oper > opers)
Definition: HM3.java:451
com.cliffc.aa.HM.HM3.HMType.HMType
HMType()
Definition: HM3.java:282
com.cliffc.aa.util.BitSetSparse.tset
boolean tset(int b0, int b1)
Definition: BitSetSparse.java:6
com.cliffc.aa.HM.HM3.Oper._args
final HMType[] _args
Definition: HM3.java:396
com.cliffc.aa.HM.HM3.Ident._vstk
VStack _vstk
Definition: HM3.java:167
com.cliffc.aa.HM.HM3.HMType.occurs_in
boolean occurs_in(VStack vstk, VBitSet dups)
Definition: HM3.java:301
com.cliffc.aa.HM.HM3.Worklist.toString
String toString()
Definition: HM3.java:111
com.cliffc.aa.HM.HM3.HMType
Definition: HM3.java:277
com.cliffc.aa.HM.HM3.Con.get_ids
void get_ids(VStack vstk, Worklist work)
Definition: HM3.java:162
com.cliffc.aa.HM.HM3.VStack.toString
String toString()
Definition: HM3.java:87
com.cliffc.aa.HM.HM3.HMVar.HMVar
HMVar()
Definition: HM3.java:325
com.cliffc.aa.HM.HM3.HMType.union
abstract HMType union(HMType t, Worklist work)
com.cliffc.aa.HM.HM3.Lambda
Definition: HM3.java:189
com.cliffc.aa.HM.HM3.Oper.Oper
Oper(String name, HMType... args)
Definition: HM3.java:397
com.cliffc.aa.HM.HM3.Ident.toString
String toString()
Definition: HM3.java:169
com.cliffc.aa.HM.HM3.Let.hm
HMType hm(Worklist work)
Definition: HM3.java:223
com.cliffc.aa.HM.HM3.Worklist._ary
final Ary< Syntax > _ary
Definition: HM3.java:104
com.cliffc
com.cliffc.aa.type.Type.toString
final String toString()
Definition: Type.java:127
com.cliffc.aa.HM.HM3.HMType.str
String str()
Definition: HM3.java:287
com.cliffc.aa.HM.HM3.HMType._u
HMType _u
Definition: HM3.java:278
com.cliffc.aa.HM.HM3.VStack.Iter.next
HMVar next()
Definition: HM3.java:98
com.cliffc.aa.util
Definition: AbstractEntry.java:1
com.cliffc.aa.HM.HM3.Con
Definition: HM3.java:156
com.cliffc.aa.type.TypeInt
Definition: TypeInt.java:9
com.cliffc.aa.HM.HM3.VStack.Iter
Definition: HM3.java:94
com.cliffc.aa.type.Type
an implementation of language AA
Definition: Type.java:94
com.cliffc.aa.type.TypeFlt
Definition: TypeFlt.java:9
com.cliffc.aa.util.Ary
Definition: Ary.java:11
com.cliffc.aa.HM.HM3.HMType.eq
final boolean eq(HMType v)
Definition: HM3.java:291
com.cliffc.aa.HM.HM3.HMVar.type
Type type()
Definition: HM3.java:327
com.cliffc.aa.HM.HM3.Syntax.add_neighbors
final void add_neighbors(Worklist work)
Definition: HM3.java:128
com.cliffc.aa.HM.HM3.Syntax.all_kids_ready
final boolean all_kids_ready()
Definition: HM3.java:135
com.cliffc.aa.HM.HM3.Let.Let
Let(String arg0, Syntax body, Syntax use)
Definition: HM3.java:219
com.cliffc.aa.HM.HM3.Apply.arg
Syntax arg()
Definition: HM3.java:250
com.cliffc.aa.HM.HM3
Definition: HM3.java:31
com.cliffc.aa.HM.HM3.Lambda.Lambda
Lambda(String arg0, Syntax body)
Definition: HM3.java:191
com.cliffc.aa.HM.HM3.HMVar._t
Type _t
Definition: HM3.java:324
com.cliffc.aa.HM.HM3.HMVar._str
SB _str(SB sb, VBitSet dups, boolean debug)
Definition: HM3.java:328
com.cliffc.aa.type.Type.ANY
static final Type ANY
Definition: Type.java:325
com.cliffc.aa.HM.HM3.HMType.fresh
HMType fresh(VStack vstk)
Definition: HM3.java:294
com.cliffc.aa.HM.HM3.Ident.progress
boolean progress()
Definition: HM3.java:177
com.cliffc.aa.HM.HM3.Syntax.progress
abstract boolean progress()
com.cliffc.aa.type.Type.meet
final Type meet(Type t)
Definition: Type.java:412
com.cliffc.aa.type.Type.str
SB str(SB sb, VBitSet dups, TypeMem mem, boolean debug)
Definition: Type.java:131
com.cliffc.aa.util.BitSetSparse
Definition: BitSetSparse.java:4
com.cliffc.aa.HM.HM3.Ident.get_ids
void get_ids(VStack vstk, Worklist work)
Definition: HM3.java:178
com.cliffc.aa.HM.HM3.HMType.find
abstract HMType find()
com.cliffc.aa.HM.HM3.HMType._ids
Ary< Ident > _ids
Definition: HM3.java:283
com.cliffc.aa.HM.HM3.Apply.get_ids
void get_ids(VStack vstk, Worklist work)
Definition: HM3.java:272
com.cliffc.aa.util.SB.unchar
SB unchar()
Definition: SB.java:58
Iterable
com.cliffc.aa.HM.HM3.Syntax._par
Syntax _par
Definition: HM3.java:116
com.cliffc.aa.HM.HM3.Worklist.addAll
void addAll(Ary<? extends Syntax > ss)
Definition: HM3.java:110
com.cliffc.aa.HM.HM3.Con._t
final Type _t
Definition: HM3.java:157
com.cliffc.aa.HM.HM3.HMType.reset
static void reset()
Definition: HM3.java:281
com.cliffc.aa.HM.HM3.Worklist.len
int len()
Definition: HM3.java:106
com.cliffc.aa.util.VBitSet.tset
boolean tset(int idx)
Definition: VBitSet.java:7
com.cliffc.aa.HM.HM3.Apply
Definition: HM3.java:247
com.cliffc.aa.HM.HM3.Con.Con
Con(Type t)
Definition: HM3.java:158
com.cliffc.aa.type.TypeInt.INT64
static final TypeInt INT64
Definition: TypeInt.java:39
com.cliffc.aa.HM.HM3.HMType._uid
final int _uid
Definition: HM3.java:279
com.cliffc.aa.HM.HM3.Let.use
Syntax use()
Definition: HM3.java:221
com.cliffc.aa.HM.HM3.Con.toString
String toString()
Definition: HM3.java:159
com.cliffc.aa.HM.HM3.Syntax
Definition: HM3.java:115
com.cliffc.aa.HM.HM3.Syntax.hm
abstract HMType hm(Worklist work)
com.cliffc.aa.HM.HM3.Lambda.toString
String toString()
Definition: HM3.java:193
com.cliffc.aa.HM.HM3.VStack.Iter.hasNext
boolean hasNext()
Definition: HM3.java:97
com.cliffc.aa.HM.HM3.ENV
static final HashMap< String, HMType > ENV
Definition: HM3.java:32
com.cliffc.aa.HM.HM3.HMVar
Definition: HM3.java:323
com.cliffc.aa.HM.HM3.Con.hm
HMType hm(Worklist work)
Definition: HM3.java:160
com.cliffc.aa.HM.HM3.Ident._name
final String _name
Definition: HM3.java:166
com.cliffc.aa.HM.HM3.Let
Definition: HM3.java:217
com.cliffc.aa.HM.HM3.VStack._par
final VStack _par
Definition: HM3.java:84
com.cliffc.aa.HM.HM3.Let.body
Syntax body()
Definition: HM3.java:220
com.cliffc.aa.HM.HM3.Oper.fun
static Oper fun(HMType... args)
Definition: HM3.java:398
com.cliffc.aa.HM.HM3.Apply.progress
boolean progress()
Definition: HM3.java:262
com.cliffc.aa.HM.HM3.Oper.find
HMType find()
Definition: HM3.java:417
com.cliffc.aa.HM.HM3.Ident
Definition: HM3.java:165
com.cliffc.aa.HM.HM3.reset
static void reset()
Definition: HM3.java:80
com.cliffc.aa.HM.HM3.HMVar.find
HMType find()
Definition: HM3.java:337
com.cliffc.aa.HM.HM3.Worklist
Definition: HM3.java:103
com.cliffc.aa.HM.HM3.Let.toString
String toString()
Definition: HM3.java:222
com.cliffc.aa.util.VBitSet
Definition: VBitSet.java:5
com.cliffc.aa.HM.HM3.Let.get_ids
void get_ids(VStack vstk, Worklist work)
Definition: HM3.java:240
com.cliffc.aa.HM.HM3.HMVar.union
HMType union(HMType that, Worklist work)
Definition: HM3.java:347
com.cliffc.aa.HM.HM3.Worklist.pop
Syntax pop()
Definition: HM3.java:108
com.cliffc.aa.HM.HM3.Let.progress
boolean progress()
Definition: HM3.java:232
NotNull
com.cliffc.aa.util.SB
Tight/tiny StringBuilder wrapper.
Definition: SB.java:8
com.cliffc.aa.HM.HM3.HMVar._eq
boolean _eq(HMType v, BitSetSparse dups)
Definition: HM3.java:375
com.cliffc.aa.HM.HM3.Lambda.get_ids
void get_ids(VStack vstk, Worklist work)
Definition: HM3.java:211
com.cliffc.aa.HM.HM3.Syntax.check_progress
boolean check_progress(Worklist work)
Definition: HM3.java:144
com.cliffc.aa.HM.HM3.HMVar.HMVar
HMVar(Type t)
Definition: HM3.java:326
com.cliffc.aa.HM.HM3.HMType.toString
final String toString()
Definition: HM3.java:286
com.cliffc.aa.HM.HM3.VStack
Definition: HM3.java:83
com.cliffc.aa.HM.HM3.Oper._eq
boolean _eq(HMType v, BitSetSparse dups)
Definition: HM3.java:432
com.cliffc.aa.HM.HM3.HMType._eq
abstract boolean _eq(HMType v, BitSetSparse dups)
com.cliffc.aa.HM.HM3.HMType.is_top
boolean is_top()
Definition: HM3.java:289
com.cliffc.aa
Definition: AA.java:1
com.cliffc.aa.HM.HM3.HMType.CNT
static int CNT
Definition: HM3.java:280
com.cliffc.aa.HM.HM3.Ident.Ident
Ident(String name)
Definition: HM3.java:168
com.cliffc.aa.HM.HM3.HMType.occurs_in
boolean occurs_in(HMType[] args, VBitSet dups)
Definition: HM3.java:306
com.cliffc.aa.HM.HM3.Syntax.add_work
final void add_work(Worklist work)
Definition: HM3.java:126
com.cliffc.aa.HM.HM3.Con.progress
boolean progress()
Definition: HM3.java:161
com.cliffc.aa.util.SB.p
SB p(String s)
Definition: SB.java:13
com.cliffc.aa.HM.HM3.Oper._str
SB _str(SB sb, VBitSet dups, boolean debug)
Definition: HM3.java:399
com.cliffc.aa.HM.HM3.Let._arg0
final String _arg0
Definition: HM3.java:218
com.cliffc.aa.HM.HM3.Oper
Definition: HM3.java:394
com.cliffc.aa.HM.HM3.HMVar._fresh
HMType _fresh(VStack vstk, HashMap< HMVar, HMVar > vars, HashMap< Oper, Oper > opers)
Definition: HM3.java:386
com.cliffc.aa.HM.HM3.HMType._str
abstract SB _str(SB sb, VBitSet vbs, boolean debug)
com.cliffc.aa.HM.HM3.Apply.hm
HMType hm(Worklist work)
Definition: HM3.java:252
com.cliffc.aa.HM.HM3.Worklist._work
final HashSet< Syntax > _work
Definition: HM3.java:105
com.cliffc.aa.HM.HM3.Lambda.progress
boolean progress()
Definition: HM3.java:200
com.cliffc.aa.HM.HM3.Apply.fun
Syntax fun()
Definition: HM3.java:249
com.cliffc.aa.HM.HM3.HMType._fresh
abstract HMType _fresh(VStack vstk, HashMap< HMVar, HMVar > vars, HashMap< Oper, Oper > opers)
com.cliffc.aa.HM.HM3.VStack.VStack
VStack(VStack par, HMVar nongen)
Definition: HM3.java:86
com.cliffc.aa.HM.HM3.Syntax.get_ids
abstract void get_ids(VStack vstk, Worklist work)
com.cliffc.aa.HM.HM3.Syntax._hm
HMType _hm
Definition: HM3.java:118
com.cliffc.aa.HM.HM3.VStack.iterator
Iterator< HMVar > iterator()
Definition: HM3.java:93
com.cliffc.aa.HM.HM3.VStack.Iter._vstk
VStack _vstk
Definition: HM3.java:95
com.cliffc.aa.HM.HM3.hm
static HMType hm(Syntax prog)
Definition: HM3.java:34
com.cliffc.aa.HM.HM3.VStack.Iter.Iter
Iter()
Definition: HM3.java:96
com.cliffc.aa.HM.HM3.Ident.hm
HMType hm(Worklist work)
Definition: HM3.java:170
com.cliffc.aa.type.TypeMemPtr.STRPTR
static final TypeMemPtr STRPTR
Definition: TypeMemPtr.java:97
com.cliffc.aa.HM.HM3.VStack.str
SB str(SB sb)
Definition: HM3.java:88
com.cliffc.aa.HM.HM3.VStack._nongen
final HMVar _nongen
Definition: HM3.java:85
com.cliffc.aa.HM.HM3.Lambda.body
Syntax body()
Definition: HM3.java:192
com
com.cliffc.aa.HM.HM3.Apply.toString
String toString()
Definition: HM3.java:251
com.cliffc.aa.HM.HM3.HMType.EQS
static final HashMap< HMVar, HMVar > EQS
Definition: HM3.java:290
com.cliffc.aa.type.TypeInt.BOOL
static final TypeInt BOOL
Definition: TypeInt.java:43
com.cliffc.aa.util.SB.toString
String toString()
Definition: SB.java:62
com.cliffc.aa.HM.HM3.HMType.occurs_in_type
boolean occurs_in_type(HMType v, VBitSet dups)
Definition: HM3.java:310
com.cliffc.aa.type
Definition: Bits.java:1
com.cliffc.aa.type.TypeMemPtr
Definition: TypeMemPtr.java:14
com.cliffc.aa.HM.HM3.Worklist.push
void push(Syntax s)
Definition: HM3.java:107
com.cliffc.aa.HM.HM3.Oper._name
final String _name
Definition: HM3.java:395
com.cliffc.aa.HM.HM3.Apply.Apply
Apply(Syntax fun, Syntax arg)
Definition: HM3.java:248
com.cliffc.aa.type.TypeFlt.FLT64
static final TypeFlt FLT64
Definition: TypeFlt.java:38
com.cliffc.aa.HM.HM3.Syntax._kids
Syntax[] _kids
Definition: HM3.java:117
com.cliffc.aa.HM.HM3.Lambda.hm
HMType hm(Worklist work)
Definition: HM3.java:194