anchor.diff:        'unlinked summarize + parse',
         unlinkedSummarizeTimer.elapsedMicroseconds +
             parseTimer.elapsedMicroseconds);
  -  report('prelink', prelinkTimer.elapsedMicroseconds);
  +  report('prelink', prelinkSummaryTimer.elapsedMicroseconds);
  +}
  +
  +/// Produces linked summaries for every file in [files] and reports the time
  +/// spent doing so.
  +void linkedSummarizeFiles(Set<Source> files) {
  +  // The code below will record again how many chars are scanned and how long it
  +  // takes to scan them, even though we already did so in [scanReachableFiles].
  +  // Recording and reporting this twice is unnecessary, but we do so for now to
  +  // validate that the results are consistent.
  +  scanTimer = new Stopwatch();
  +  var old = scanTotalChars;
  +  scanTotalChars = 0;
  +  parseTimer = new Stopwatch();
  +  unlinkedSummarizeTimer = new Stopwatch();
  +  var unlinkedSummaries = generateUnlinkedSummaries(files);
  +  prelinkSummaryTimer = new Stopwatch();
  +  Map<String, LinkedLibraryBuilder> prelinkedLibraries =
  +      prelinkSummaries(files, unlinkedSummaries);
  +  var linkTimer = new Stopwatch()..start();
  +  LinkedLibrary getDependency(String uri) {
  +    // getDependency should never be called because all dependencies are present
  +    // in [prelinkedLibraries].
  +    print('Warning: getDependency called for: $uri');
  +    return null;
  +  }
  +
  +  bool strong = true;
  +  relink(prelinkedLibraries, getDependency, unlinkedSummaries.getUnit, strong);
  +  linkTimer.stop();
  +
  +  if (old != scanTotalChars) print('input size changed? ${old} chars');
  +  report("scan", scanTimer.elapsedMicroseconds);
  +  report("parse", parseTimer.elapsedMicroseconds);
  +  report('unlinked summarize', unlinkedSummarizeTimer.elapsedMicroseconds);
  +  report(
  +      'unlinked summarize + parse',
  +      unlinkedSummarizeTimer.elapsedMicroseconds +
  +          parseTimer.elapsedMicroseconds);
  +  report('prelink', prelinkSummaryTimer.elapsedMicroseconds);
  +  report('link', linkTimer.elapsedMicroseconds);
  +}
  +
  +/// Prelinks all the summaries for [files], using [unlinkedSummaries] to obtain
  +/// their unlinked summaries.
  +///
  +/// The return value is suitable for passing to the summary linker.
  +Map<String, LinkedLibraryBuilder> prelinkSummaries(
  +    Set<Source> files, UnlinkedSummaries unlinkedSummaries) {
  +  prelinkSummaryTimer.start();
  +  Set<String> libraryUris =
  +      files.map((source) => source.uri.toString()).toSet();
  +
  +  String getDeclaredVariable(String s) => null;
  +  var prelinkedLibraries =
  +      setupForLink(libraryUris, unlinkedSummaries.getUnit, getDeclaredVariable);
  +  prelinkSummaryTimer.stop();
  +  return prelinkedLibraries;
   }
   
   /// Add to [files] all sources reachable from [start].
  
positive.code:       'unlinked summarize + parse',
        unlinkedSummarizeTimer.elapsedMicroseconds +
            parseTimer.elapsedMicroseconds);
  }
  
  /// Produces prelinked summaries for every file in [files] and reports the time
  
negative.code: import 'package:analyzer/src/generated/source_io.dart';
  import 'package:analyzer/src/summary/format.dart';
  import 'package:analyzer/src/summary/idl.dart';
  import 'package:analyzer/src/summary/link.dart';
  import 'package:analyzer/src/summary/summarize_ast.dart';
  import 'package:kernel/analyzer/loader.dart';
  import 'package:kernel/kernel.dart';
  