anchor.diff:  }
   
   /// Scans every file in [files] and reports the time spent doing so.
  -void scanFiles(Set<Source> files) {
  +void scanFiles<T>(Set<T> files, void Function(T) scannerFunction) {
     // `tokenize` records how many chars are scanned and how long it takes to scan
     // them. As this function is called repeatedly when running as a benchmark, we
     // make sure to clear the data and compute it again every time.
     scanTimer = new Stopwatch();
     for (var source in files) {
  -    tokenize(source);
  +    scannerFunction(source);
     }
   
     report('scan', scanTimer.elapsedMicroseconds);
  
positive.code: 
    setup(path.fromUri(entryUri));
  
    Set<Source> files = scanReachableFiles(entryUri);
    var handlers = {
      'scan': () async => scanFiles(files),
      'parse': () async => parseFiles(files),
    };
  
    var handler = handlers[bench];
    if (handler == null) {
  
negative.code:   return result;
  }
  
  ScannerResult tokenizeBytes(Uint8List source) {
    scanTimer.start();
    ScannerResult result = scan(source, includeComments: false);
    var token = result.tokens;
    if (result.hasErrors) {
      // Ignore errors.
      while (token is ErrorToken) {
        token = token.next!;
      }
    }
    scanTimer.stop();
    return result;
  }
  
  String _findSdkPath() {
    var executable = Platform.resolvedExecutable;
    var executableDir = path.dirname(executable);
  