Skip to content

Commit 830992d

Browse files
committed
1 parent 4130056 commit 830992d

1 file changed

Lines changed: 26 additions & 19 deletions

File tree

extensions/git/src/git.ts

Lines changed: 26 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -327,6 +327,12 @@ function getGitErrorCode(stderr: string): string | undefined {
327327
return undefined;
328328
}
329329

330+
// https://github.com/microsoft/vscode/issues/89373
331+
// https://github.com/git-for-windows/git/issues/2478
332+
function sanitizePath(path: string): string {
333+
return path.replace(/^([a-z]):\\/i, (_, letter) => `${letter.toUpperCase()}:\\`);
334+
}
335+
330336
const COMMIT_FORMAT = '%H\n%aN\n%aE\n%at\n%P\n%B';
331337

332338
export class Git {
@@ -496,6 +502,10 @@ export class Git {
496502
LANG: 'en_US.UTF-8'
497503
});
498504

505+
if (options.cwd) {
506+
options.cwd = sanitizePath(options.cwd);
507+
}
508+
499509
if (options.log !== false) {
500510
this.log(`> git ${args.join(' ')}\n`);
501511
}
@@ -887,12 +897,12 @@ export class Repository {
887897
}
888898

889899
async lstree(treeish: string, path: string): Promise<LsTreeElement[]> {
890-
const { stdout } = await this.run(['ls-tree', '-l', treeish, '--', path]);
900+
const { stdout } = await this.run(['ls-tree', '-l', treeish, '--', sanitizePath(path)]);
891901
return parseLsTree(stdout);
892902
}
893903

894904
async lsfiles(path: string): Promise<LsFilesElement[]> {
895-
const { stdout } = await this.run(['ls-files', '--stage', '--', path]);
905+
const { stdout } = await this.run(['ls-files', '--stage', '--', sanitizePath(path)]);
896906
return parseLsFiles(stdout);
897907
}
898908

@@ -986,7 +996,7 @@ export class Repository {
986996
return await this.diffFiles(false);
987997
}
988998

989-
const args = ['diff', '--', path];
999+
const args = ['diff', '--', sanitizePath(path)];
9901000
const result = await this.run(args);
9911001
return result.stdout;
9921002
}
@@ -999,7 +1009,7 @@ export class Repository {
9991009
return await this.diffFiles(false, ref);
10001010
}
10011011

1002-
const args = ['diff', ref, '--', path];
1012+
const args = ['diff', ref, '--', sanitizePath(path)];
10031013
const result = await this.run(args);
10041014
return result.stdout;
10051015
}
@@ -1012,7 +1022,7 @@ export class Repository {
10121022
return await this.diffFiles(true);
10131023
}
10141024

1015-
const args = ['diff', '--cached', '--', path];
1025+
const args = ['diff', '--cached', '--', sanitizePath(path)];
10161026
const result = await this.run(args);
10171027
return result.stdout;
10181028
}
@@ -1025,7 +1035,7 @@ export class Repository {
10251035
return await this.diffFiles(true, ref);
10261036
}
10271037

1028-
const args = ['diff', '--cached', ref, '--', path];
1038+
const args = ['diff', '--cached', ref, '--', sanitizePath(path)];
10291039
const result = await this.run(args);
10301040
return result.stdout;
10311041
}
@@ -1045,7 +1055,7 @@ export class Repository {
10451055
return await this.diffFiles(false, range);
10461056
}
10471057

1048-
const args = ['diff', range, '--', path];
1058+
const args = ['diff', range, '--', sanitizePath(path)];
10491059
const result = await this.run(args);
10501060

10511061
return result.stdout.trim();
@@ -1158,7 +1168,7 @@ export class Repository {
11581168
args.push('--');
11591169

11601170
if (paths && paths.length) {
1161-
args.push.apply(args, paths);
1171+
args.push.apply(args, paths.map(sanitizePath));
11621172
} else {
11631173
args.push('.');
11641174
}
@@ -1173,13 +1183,13 @@ export class Repository {
11731183
return;
11741184
}
11751185

1176-
args.push(...paths);
1186+
args.push(...paths.map(sanitizePath));
11771187

11781188
await this.run(args);
11791189
}
11801190

11811191
async stage(path: string, data: string): Promise<void> {
1182-
const child = this.stream(['hash-object', '--stdin', '-w', '--path', path], { stdio: [null, null, null] });
1192+
const child = this.stream(['hash-object', '--stdin', '-w', '--path', sanitizePath(path)], { stdio: [null, null, null] });
11831193
child.stdin!.end(data, 'utf8');
11841194

11851195
const { exitCode, stdout } = await exec(child);
@@ -1224,7 +1234,7 @@ export class Repository {
12241234

12251235
try {
12261236
if (paths && paths.length > 0) {
1227-
for (const chunk of splitInChunks(paths, MAX_CLI_LENGTH)) {
1237+
for (const chunk of splitInChunks(paths.map(sanitizePath), MAX_CLI_LENGTH)) {
12281238
await this.run([...args, '--', ...chunk]);
12291239
}
12301240
} else {
@@ -1363,7 +1373,7 @@ export class Repository {
13631373
}
13641374

13651375
async clean(paths: string[]): Promise<void> {
1366-
const pathsByGroup = groupBy(paths, p => path.dirname(p));
1376+
const pathsByGroup = groupBy(paths.map(sanitizePath), p => path.dirname(p));
13671377
const groups = Object.keys(pathsByGroup).map(k => pathsByGroup[k]);
13681378

13691379
const limiter = new Limiter(5);
@@ -1409,7 +1419,7 @@ export class Repository {
14091419
}
14101420

14111421
if (paths && paths.length) {
1412-
args.push.apply(args, paths);
1422+
args.push.apply(args, paths.map(sanitizePath));
14131423
} else {
14141424
args.push('.');
14151425
}
@@ -1560,11 +1570,8 @@ export class Repository {
15601570

15611571
async blame(path: string): Promise<string> {
15621572
try {
1563-
const args = ['blame'];
1564-
args.push(path);
1565-
1566-
let result = await this.run(args);
1567-
1573+
const args = ['blame', sanitizePath(path)];
1574+
const result = await this.run(args);
15681575
return result.stdout.trim();
15691576
} catch (err) {
15701577
if (/^fatal: no such path/.test(err.stderr || '')) {
@@ -1894,7 +1901,7 @@ export class Repository {
18941901
async updateSubmodules(paths: string[]): Promise<void> {
18951902
const args = ['submodule', 'update', '--'];
18961903

1897-
for (const chunk of splitInChunks(paths, MAX_CLI_LENGTH)) {
1904+
for (const chunk of splitInChunks(paths.map(sanitizePath), MAX_CLI_LENGTH)) {
18981905
await this.run([...args, ...chunk]);
18991906
}
19001907
}

0 commit comments

Comments
 (0)