@@ -517,20 +517,71 @@ abstract module BtreeInv {
517517 }
518518 }
519519
520+ lemma pivotsAreCorrectAfterSplit (tree: Node , newtree: Node , l: Key , u: Key , childrenToLeft: int , pos: int )
521+ requires WFTree (tree);
522+ requires SplitTransform (tree, newtree, l, u, childrenToLeft);
523+ requires pos == Keyspace. LargestLte (tree.pivots, l) + 1;
524+ requires 0 <= pos < |tree. children|;
525+ requires tree. children[pos]. lb == l;
526+ requires tree. children[pos]. ub == u;
527+ ensures Keyspace. IsStrictlySorted (newtree.pivots);
528+ {
529+ var child := tree. children[pos];
530+ assert |newtree. children| == |tree. children| + 1;
531+ var left_child := newtree. children[pos];
532+ var right_child := newtree. children[pos+ 1];
533+ assert WFTree (child);
534+ if (pos < |tree. pivots|) {
535+ if (child. Leaf?) {
536+ assert newtree. pivots[pos]
537+ == right_child. keys[0]
538+ == child. keys[childrenToLeft];
539+ assert Keyspace. lt (child.keys[childrenToLeft], child.ub);
540+ } else {
541+ assert newtree. pivots[pos] == child. pivots[childrenToLeft- 1];
542+ assert Keyspace. lt (child.pivots[childrenToLeft-1], child.ub);
543+ }
544+ assert child. ub == tree. pivots[pos];
545+ assert Keyspace. lt (newtree.pivots[pos], tree.pivots[pos]);
546+ }
547+ if (pos > 0) {
548+ if (child. Leaf?) {
549+ assert Keyspace. lte (child.lb, child.keys[0]);
550+ Keyspace. reveal_IsStrictlySorted ();
551+ assert Keyspace. lt (child.keys[0], child.keys[childrenToLeft]);
552+ assert Keyspace. lt (child.lb, child.keys[childrenToLeft]);
553+ } else {
554+ assert Keyspace. lt (child.lb, child.pivots[childrenToLeft-1]);
555+ }
556+ assert child. lb == tree. pivots[pos- 1];
557+ assert Keyspace. lt (tree.pivots[pos-1], newtree.pivots[pos]);
558+ }
559+ Keyspace. strictlySortedInsert2 (tree.pivots, newtree.pivots[pos], pos);
560+ }
561+
520562 lemma SplitIsCorrect< Value> (tree: Node, newtree: Node, l: Key, u: Key, childrenToLeft: int )
521563 requires WFTree (tree);
522564 requires CantEquivocate (tree);
523565 requires SplitTransform (tree, newtree, l, u, childrenToLeft);
566+ ensures WFTree (newtree);
524567 ensures PreservesLookups (tree, newtree);
525568 ensures PreservesLookups (newtree, tree);
526- ensures WFTree (newtree)
527- ensures CantEquivocate (newtree)
528- decreases tree
569+ ensures CantEquivocate (newtree);
570+ decreases tree;
529571 {
530572 var pos := Keyspace. LargestLte (tree.pivots, l) + 1;
531573 var child := tree. children[pos];
532574 if (child. lb == l && child. ub == u) {
575+ var left_child := newtree. children[pos];
576+ var right_child := newtree. children[pos+ 1];
577+ pivotsAreCorrectAfterSplit (tree, newtree, l, u, childrenToLeft, pos);
578+ assert WFTree (newtree);
579+ assume false ;
580+ assert PreservesLookups (tree, newtree);
581+ assert PreservesLookups (newtree, tree);
582+ assert CantEquivocate (newtree);
533583 } else {
584+ assume false ;
534585 // Before we can call Define recursively, we must prove that the child CantEquivocate.
535586 forall key', valueA, valueB, lookup, lookup'
536587 |
0 commit comments