Commit e6bafd0b authored by Chris Bracken's avatar Chris Bracken Committed by GitHub

Support space- and backslash-escaped dependencies (#11090)

Snapshot dependency files now backslash-escape dependency paths
containing spaces and backslashes.

See: https://codereview.chromium.org/2966903003/
parent 177cf912
......@@ -44,20 +44,27 @@ class Checksum {
int get hashCode => _checksums.hashCode;
}
final RegExp _separatorExpr = new RegExp(r'([^\\]) ');
final RegExp _escapeExpr = new RegExp(r'\\(.)');
/// Parses a VM snapshot dependency file.
///
/// Snapshot dependency files are a single line mapping the output snapshot to a
/// space-separated list of input files used to generate that output. e.g,
/// space-separated list of input files used to generate that output. Spaces and
/// backslashes are escaped with a backslash. e.g,
///
/// outfile : file1.dart fil\\e2.dart fil\ e3.dart
///
/// outfile : file1.dart file2.dart file3.dart
/// will return a set containing: 'file1.dart', 'fil\e2.dart', 'fil e3.dart'.
Future<Set<String>> readDepfile(String depfilePath) async {
// Depfile format:
// outfile1 outfile2 : file1.dart file2.dart file3.dart
final String contents = await fs.file(depfilePath).readAsString();
final String dependencies = contents.split(': ')[1];
return dependencies
.split(' ')
.map((String path) => path.trim())
.replaceAllMapped(_separatorExpr, (Match match) => '${match.group(1)}\n')
.split('\n')
.map((String path) => path.replaceAllMapped(_escapeExpr, (Match match) => match.group(1)).trim())
.where((String path) => path.isNotEmpty)
.toSet();
}
......@@ -64,4 +64,43 @@ void main() {
});
});
});
group('readDepfile', () {
MemoryFileSystem fs;
setUp(() {
fs = new MemoryFileSystem();
});
testUsingContext('returns one file if only one is listed', () async {
await fs.file('a.d').writeAsString('snapshot.d: /foo/a.dart');
expect(await readDepfile('a.d'), unorderedEquals(<String>['/foo/a.dart']));
}, overrides: <Type, Generator>{ FileSystem: () => fs});
testUsingContext('returns multiple files', () async {
await fs.file('a.d').writeAsString('snapshot.d: /foo/a.dart /foo/b.dart');
expect(await readDepfile('a.d'), unorderedEquals(<String>[
'/foo/a.dart',
'/foo/b.dart',
]));
}, overrides: <Type, Generator>{ FileSystem: () => fs});
testUsingContext('trims extra spaces between files', () async {
await fs.file('a.d').writeAsString('snapshot.d: /foo/a.dart /foo/b.dart /foo/c.dart');
expect(await readDepfile('a.d'), unorderedEquals(<String>[
'/foo/a.dart',
'/foo/b.dart',
'/foo/c.dart',
]));
}, overrides: <Type, Generator>{ FileSystem: () => fs});
testUsingContext('returns files with spaces and backslashes', () async {
await fs.file('a.d').writeAsString(r'snapshot.d: /foo/a\ a.dart /foo/b\\b.dart /foo/c\\ c.dart');
expect(await readDepfile('a.d'), unorderedEquals(<String>[
r'/foo/a a.dart',
r'/foo/b\b.dart',
r'/foo/c\ c.dart',
]));
}, overrides: <Type, Generator>{ FileSystem: () => fs});
});
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment