src/share/classes/com/sun/tools/javac/comp/Infer.java

changeset 1891
42b3c5e92461
parent 1853
831467c4c6a7
child 1896
44e27378f523
equal deleted inserted replaced
1890:bfbedbfc522a 1891:42b3c5e92461
416 * Check bounds and perform incorporation 416 * Check bounds and perform incorporation
417 */ 417 */
418 void checkWithinBounds(InferenceContext inferenceContext, 418 void checkWithinBounds(InferenceContext inferenceContext,
419 Warner warn) throws InferenceException { 419 Warner warn) throws InferenceException {
420 MultiUndetVarListener mlistener = new MultiUndetVarListener(inferenceContext.undetvars); 420 MultiUndetVarListener mlistener = new MultiUndetVarListener(inferenceContext.undetvars);
421 List<Type> saved_undet = inferenceContext.save();
421 try { 422 try {
422 while (true) { 423 while (true) {
423 mlistener.reset(); 424 mlistener.reset();
424 if (!allowGraphInference) { 425 if (!allowGraphInference) {
425 //in legacy mode we lack of transitivity, so bound check 426 //in legacy mode we lack of transitivity, so bound check
441 if (!mlistener.changed || !allowGraphInference) break; 442 if (!mlistener.changed || !allowGraphInference) break;
442 } 443 }
443 } 444 }
444 finally { 445 finally {
445 mlistener.detach(); 446 mlistener.detach();
447 if (mlistener.rounds == MAX_INCORPORATION_STEPS) {
448 inferenceContext.rollback(saved_undet);
449 }
446 } 450 }
447 } 451 }
448 //where 452 //where
449 /** 453 /**
450 * This listener keeps track of changes on a group of inference variable 454 * This listener keeps track of changes on a group of inference variable
643 for (Type b : uv.getBounds(InferenceBound.UPPER)) { 647 for (Type b : uv.getBounds(InferenceBound.UPPER)) {
644 if (inferenceContext.inferenceVars().contains(b)) { 648 if (inferenceContext.inferenceVars().contains(b)) {
645 UndetVar uv2 = (UndetVar)inferenceContext.asFree(b); 649 UndetVar uv2 = (UndetVar)inferenceContext.asFree(b);
646 //alpha <: beta 650 //alpha <: beta
647 //0. set beta :> alpha 651 //0. set beta :> alpha
648 uv2.addBound(InferenceBound.LOWER, uv.qtype, infer.types); 652 uv2.addBound(InferenceBound.LOWER, uv, infer.types);
649 //1. copy alpha's lower to beta's 653 //1. copy alpha's lower to beta's
650 for (Type l : uv.getBounds(InferenceBound.LOWER)) { 654 for (Type l : uv.getBounds(InferenceBound.LOWER)) {
651 uv2.addBound(InferenceBound.LOWER, inferenceContext.asInstType(l), infer.types); 655 uv2.addBound(InferenceBound.LOWER, inferenceContext.asInstType(l), infer.types);
652 } 656 }
653 //2. copy beta's upper to alpha's 657 //2. copy beta's upper to alpha's
668 for (Type b : uv.getBounds(InferenceBound.LOWER)) { 672 for (Type b : uv.getBounds(InferenceBound.LOWER)) {
669 if (inferenceContext.inferenceVars().contains(b)) { 673 if (inferenceContext.inferenceVars().contains(b)) {
670 UndetVar uv2 = (UndetVar)inferenceContext.asFree(b); 674 UndetVar uv2 = (UndetVar)inferenceContext.asFree(b);
671 //alpha :> beta 675 //alpha :> beta
672 //0. set beta <: alpha 676 //0. set beta <: alpha
673 uv2.addBound(InferenceBound.UPPER, uv.qtype, infer.types); 677 uv2.addBound(InferenceBound.UPPER, uv, infer.types);
674 //1. copy alpha's upper to beta's 678 //1. copy alpha's upper to beta's
675 for (Type u : uv.getBounds(InferenceBound.UPPER)) { 679 for (Type u : uv.getBounds(InferenceBound.UPPER)) {
676 uv2.addBound(InferenceBound.UPPER, inferenceContext.asInstType(u), infer.types); 680 uv2.addBound(InferenceBound.UPPER, inferenceContext.asInstType(u), infer.types);
677 } 681 }
678 //2. copy beta's lower to alpha's 682 //2. copy beta's lower to alpha's
693 for (Type b : uv.getBounds(InferenceBound.EQ)) { 697 for (Type b : uv.getBounds(InferenceBound.EQ)) {
694 if (inferenceContext.inferenceVars().contains(b)) { 698 if (inferenceContext.inferenceVars().contains(b)) {
695 UndetVar uv2 = (UndetVar)inferenceContext.asFree(b); 699 UndetVar uv2 = (UndetVar)inferenceContext.asFree(b);
696 //alpha == beta 700 //alpha == beta
697 //0. set beta == alpha 701 //0. set beta == alpha
698 uv2.addBound(InferenceBound.EQ, uv.qtype, infer.types); 702 uv2.addBound(InferenceBound.EQ, uv, infer.types);
699 //1. copy all alpha's bounds to beta's 703 //1. copy all alpha's bounds to beta's
700 for (InferenceBound ib : InferenceBound.values()) { 704 for (InferenceBound ib : InferenceBound.values()) {
701 for (Type b2 : uv.getBounds(ib)) { 705 for (Type b2 : uv.getBounds(ib)) {
702 if (b2 != uv2) { 706 if (b2 != uv2) {
703 uv2.addBound(ib, inferenceContext.asInstType(b2), infer.types); 707 uv2.addBound(ib, inferenceContext.asInstType(b2), infer.types);
1088 checkWithinBounds(inferenceContext, warn); //initial propagation of bounds 1092 checkWithinBounds(inferenceContext, warn); //initial propagation of bounds
1089 InferenceGraph inferenceGraph = new InferenceGraph(); 1093 InferenceGraph inferenceGraph = new InferenceGraph();
1090 while (!sstrategy.done()) { 1094 while (!sstrategy.done()) {
1091 InferenceGraph.Node nodeToSolve = sstrategy.pickNode(inferenceGraph); 1095 InferenceGraph.Node nodeToSolve = sstrategy.pickNode(inferenceGraph);
1092 List<Type> varsToSolve = List.from(nodeToSolve.data); 1096 List<Type> varsToSolve = List.from(nodeToSolve.data);
1093 inferenceContext.save(); 1097 List<Type> saved_undet = inferenceContext.save();
1094 try { 1098 try {
1095 //repeat until all variables are solved 1099 //repeat until all variables are solved
1096 outer: while (Type.containsAny(inferenceContext.restvars(), varsToSolve)) { 1100 outer: while (Type.containsAny(inferenceContext.restvars(), varsToSolve)) {
1097 //for each inference phase 1101 //for each inference phase
1098 for (GraphInferenceSteps step : GraphInferenceSteps.values()) { 1102 for (GraphInferenceSteps step : GraphInferenceSteps.values()) {
1105 throw inferenceException.setMessage(); 1109 throw inferenceException.setMessage();
1106 } 1110 }
1107 } 1111 }
1108 catch (InferenceException ex) { 1112 catch (InferenceException ex) {
1109 //did we fail because of interdependent ivars? 1113 //did we fail because of interdependent ivars?
1110 inferenceContext.rollback(); 1114 inferenceContext.rollback(saved_undet);
1111 instantiateAsUninferredVars(varsToSolve, inferenceContext); 1115 instantiateAsUninferredVars(varsToSolve, inferenceContext);
1112 checkWithinBounds(inferenceContext, warn); 1116 checkWithinBounds(inferenceContext, warn);
1113 } 1117 }
1114 inferenceGraph.deleteNode(nodeToSolve); 1118 inferenceGraph.deleteNode(nodeToSolve);
1115 } 1119 }
1500 } 1504 }
1501 1505
1502 /** 1506 /**
1503 * Save the state of this inference context 1507 * Save the state of this inference context
1504 */ 1508 */
1505 void save() { 1509 List<Type> save() {
1506 ListBuffer<Type> buf = ListBuffer.lb(); 1510 ListBuffer<Type> buf = ListBuffer.lb();
1507 for (Type t : undetvars) { 1511 for (Type t : undetvars) {
1508 UndetVar uv = (UndetVar)t; 1512 UndetVar uv = (UndetVar)t;
1509 UndetVar uv2 = new UndetVar((TypeVar)uv.qtype, types); 1513 UndetVar uv2 = new UndetVar((TypeVar)uv.qtype, types);
1510 for (InferenceBound ib : InferenceBound.values()) { 1514 for (InferenceBound ib : InferenceBound.values()) {
1513 } 1517 }
1514 } 1518 }
1515 uv2.inst = uv.inst; 1519 uv2.inst = uv.inst;
1516 buf.add(uv2); 1520 buf.add(uv2);
1517 } 1521 }
1518 saved_undet = buf.toList(); 1522 return buf.toList();
1519 } 1523 }
1520 1524
1521 /** 1525 /**
1522 * Restore the state of this inference context to the previous known checkpoint 1526 * Restore the state of this inference context to the previous known checkpoint
1523 */ 1527 */
1524 void rollback() { 1528 void rollback(List<Type> saved_undet) {
1525 Assert.check(saved_undet != null && saved_undet.length() == undetvars.length()); 1529 Assert.check(saved_undet != null && saved_undet.length() == undetvars.length());
1526 undetvars = saved_undet; 1530 //restore bounds (note: we need to preserve the old instances)
1527 saved_undet = null; 1531 for (Type t : undetvars) {
1532 UndetVar uv = (UndetVar)t;
1533 UndetVar uv_saved = (UndetVar)saved_undet.head;
1534 for (InferenceBound ib : InferenceBound.values()) {
1535 uv.setBounds(ib, uv_saved.getBounds(ib));
1536 }
1537 uv.inst = uv_saved.inst;
1538 saved_undet = saved_undet.tail;
1539 }
1528 } 1540 }
1529 1541
1530 /** 1542 /**
1531 * Copy variable in this inference context to the given context 1543 * Copy variable in this inference context to the given context
1532 */ 1544 */

mercurial