anchor.diff:    SourceCode end() {
       if (_chunks.isNotEmpty) {
         _writeHardSplit();
  -      _completeLine(_chunks.length);
  +      _splitLines();
       }
   
       // Be a good citizen, end with a newline.
  
positive.code:       }
      }
  
      return _hardenRules(rulesToHarden, length);
  
      // TODO(bob): What if the rules are still in effect? Should we replace them
      // in _rules too?
    }
  
    /// Hardens every chunk in the first [length] chunks that uses one of [rules].
    ///
    /// Returns the list of lengths within [length] that can now be split as
    /// separate lines.
    List<int> _hardenRules(Set<Rule> rules, int length) {
      var lengths = [];
      for (var i = 0; i < length; i++) {
        var chunk = _chunks[i];
        if (rules.contains(chunk.rule)) {
          chunk.harden();
          if (_canEndLineAfter(i + 1)) lengths.add(i + 1);
        }
      }
  
      // Remove implied references to hardened rules. If a rule implies one
      // that's already hardened, we don't need to track the implication anymore.
      for (var chunk in _chunks) {
        chunk.rule.implies.removeAll(rules);
      }
  
      return lengths;
    }
  
    /// Handles open multisplits and spans when a hard line occurs.
    ///
    /// Any active separable multisplits will get split in two at this point.
    /// Other multisplits are forced into the "hard" state. All of their previous
    /// splits are turned into explicit hard splits and any new splits for that
    /// multisplit become hard splits too.
    ///
    /// All open spans get discarded since they will never be satisfied.
    void _handleHardSplit() {
      // Discard all open spans. We don't remove them from the stack so that we
      // can still correctly count later calls to endSpan().
      for (var i = 0; i < _openSpans.length; i++) {
        _openSpans[i] = null;
      }
  
      // Replace each ongoing rule with a hard split if it wants to split when
      // it contains an inner split.
      var hardenedRules = new Set();
  
negative.code:       nestingMap[nestingLevels[i]] = i;
      }
  
      for (var chunk in chunks) {
        chunk.nesting = nestingMap[chunk.nesting];
      }
    }
  
    /// Preemptively hardens rules in the range of chunks from [start] to [end]
    /// (half-inclusive) if there will certainly be no solution that allows them
    /// to remain unsplit.
    ///
    /// For each rule, we look at the span of chunks it covers. If that range is
    /// longer than the page width, than the rule is preemptively hardened now.
  