Skip to content

Commit 9209bf6

Browse files
committed
path: fix input type checking regression
Before b212be0, input types were not checked in some path functions and the inputs were passed directly to `regexp.exec()` which implicitly converts its argument to a string. This commit both removes the type checking added in b212be0 and adds string coercion for those functions. PR-URL: #5244 Reviewed-By: Myles Borins <[email protected]> Reviewed-By: Rod Vagg <[email protected]> Reviewed-By: James M Snell <[email protected]> Reviewed-By: Sakthipriyan Vairamani <[email protected]>
1 parent 9221201 commit 9209bf6

File tree

2 files changed

+58
-7
lines changed

2 files changed

+58
-7
lines changed

lib/path.js

+13-7
Original file line numberDiff line numberDiff line change
@@ -698,7 +698,8 @@ const win32 = {
698698

699699

700700
dirname: function dirname(path) {
701-
assertPath(path);
701+
if (typeof path !== 'string')
702+
path = '' + path;
702703
const len = path.length;
703704
if (len === 0)
704705
return '.';
@@ -791,7 +792,7 @@ const win32 = {
791792

792793
if (end === -1) {
793794
if (rootEnd === -1)
794-
end = len;
795+
return '.';
795796
else
796797
end = rootEnd;
797798
}
@@ -800,9 +801,10 @@ const win32 = {
800801

801802

802803
basename: function basename(path, ext) {
803-
assertPath(path);
804804
if (ext !== undefined && typeof ext !== 'string')
805805
throw new TypeError('"ext" argument must be a string');
806+
if (typeof path !== 'string')
807+
path = '' + path;
806808
var start = 0;
807809
var end = -1;
808810
var matchedSlash = true;
@@ -888,7 +890,8 @@ const win32 = {
888890

889891

890892
extname: function extname(path) {
891-
assertPath(path);
893+
if (typeof path !== 'string')
894+
path = '' + path;
892895
var startDot = -1;
893896
var startPart = 0;
894897
var end = -1;
@@ -1321,7 +1324,8 @@ const posix = {
13211324

13221325

13231326
dirname: function dirname(path) {
1324-
assertPath(path);
1327+
if (typeof path !== 'string')
1328+
path = '' + path;
13251329
if (path.length === 0)
13261330
return '.';
13271331
var code = path.charCodeAt(0);
@@ -1350,9 +1354,10 @@ const posix = {
13501354

13511355

13521356
basename: function basename(path, ext) {
1353-
assertPath(path);
13541357
if (ext !== undefined && typeof ext !== 'string')
13551358
throw new TypeError('"ext" argument must be a string');
1359+
if (typeof path !== 'string')
1360+
path = '' + path;
13561361

13571362
var start = 0;
13581363
var end = -1;
@@ -1426,7 +1431,8 @@ const posix = {
14261431

14271432

14281433
extname: function extname(path) {
1429-
assertPath(path);
1434+
if (typeof path !== 'string')
1435+
path = '' + path;
14301436
var startDot = -1;
14311437
var startPart = 0;
14321438
var end = -1;

test/parallel/test-path.js

+45
Original file line numberDiff line numberDiff line change
@@ -22,13 +22,25 @@ assert.equal(path.win32.basename('\\basename.ext'), 'basename.ext');
2222
assert.equal(path.win32.basename('basename.ext'), 'basename.ext');
2323
assert.equal(path.win32.basename('basename.ext\\'), 'basename.ext');
2424
assert.equal(path.win32.basename('basename.ext\\\\'), 'basename.ext');
25+
assert.equal(path.win32.basename('foo'), 'foo');
26+
assert.equal(path.win32.basename(null), 'null');
27+
assert.equal(path.win32.basename(true), 'true');
28+
assert.equal(path.win32.basename(1), '1');
29+
assert.equal(path.win32.basename(), 'undefined');
30+
assert.equal(path.win32.basename({}), '[object Object]');
2531

2632
// On unix a backslash is just treated as any other character.
2733
assert.equal(path.posix.basename('\\dir\\basename.ext'), '\\dir\\basename.ext');
2834
assert.equal(path.posix.basename('\\basename.ext'), '\\basename.ext');
2935
assert.equal(path.posix.basename('basename.ext'), 'basename.ext');
3036
assert.equal(path.posix.basename('basename.ext\\'), 'basename.ext\\');
3137
assert.equal(path.posix.basename('basename.ext\\\\'), 'basename.ext\\\\');
38+
assert.equal(path.posix.basename('foo'), 'foo');
39+
assert.equal(path.posix.basename(null), 'null');
40+
assert.equal(path.posix.basename(true), 'true');
41+
assert.equal(path.posix.basename(1), '1');
42+
assert.equal(path.posix.basename(), 'undefined');
43+
assert.equal(path.posix.basename({}), '[object Object]');
3244

3345
// POSIX filenames may include control characters
3446
// c.f. http://www.dwheeler.com/essays/fixing-unix-linux-filenames.html
@@ -47,6 +59,12 @@ assert.equal(path.posix.dirname('/a'), '/');
4759
assert.equal(path.posix.dirname(''), '.');
4860
assert.equal(path.posix.dirname('/'), '/');
4961
assert.equal(path.posix.dirname('////'), '/');
62+
assert.equal(path.posix.dirname('foo'), '.');
63+
assert.equal(path.posix.dirname(null), '.');
64+
assert.equal(path.posix.dirname(true), '.');
65+
assert.equal(path.posix.dirname(1), '.');
66+
assert.equal(path.posix.dirname(), '.');
67+
assert.equal(path.posix.dirname({}), '.');
5068

5169
assert.equal(path.win32.dirname('c:\\'), 'c:\\');
5270
assert.equal(path.win32.dirname('c:\\foo'), 'c:\\');
@@ -81,6 +99,12 @@ assert.equal(path.win32.dirname('/a'), '/');
8199
assert.equal(path.win32.dirname(''), '.');
82100
assert.equal(path.win32.dirname('/'), '/');
83101
assert.equal(path.win32.dirname('////'), '/');
102+
assert.equal(path.win32.dirname('foo'), '.');
103+
assert.equal(path.win32.dirname(null), '.');
104+
assert.equal(path.win32.dirname(true), '.');
105+
assert.equal(path.win32.dirname(1), '.');
106+
assert.equal(path.win32.dirname(), '.');
107+
assert.equal(path.win32.dirname({}), '.');
84108

85109

86110
// path.extname tests
@@ -156,6 +180,11 @@ assert.equal(path.win32.extname('file\\'), '');
156180
assert.equal(path.win32.extname('file\\\\'), '');
157181
assert.equal(path.win32.extname('file.\\'), '.');
158182
assert.equal(path.win32.extname('file.\\\\'), '.');
183+
assert.equal(path.win32.extname(null), '');
184+
assert.equal(path.win32.extname(true), '');
185+
assert.equal(path.win32.extname(1), '');
186+
assert.equal(path.win32.extname(), '');
187+
assert.equal(path.win32.extname({}), '');
159188

160189
// On *nix, backslash is a valid name component like any other character.
161190
assert.equal(path.posix.extname('.\\'), '');
@@ -166,6 +195,11 @@ assert.equal(path.posix.extname('file\\'), '');
166195
assert.equal(path.posix.extname('file\\\\'), '');
167196
assert.equal(path.posix.extname('file.\\'), '.\\');
168197
assert.equal(path.posix.extname('file.\\\\'), '.\\\\');
198+
assert.equal(path.posix.extname(null), '');
199+
assert.equal(path.posix.extname(true), '');
200+
assert.equal(path.posix.extname(1), '');
201+
assert.equal(path.posix.extname(), '');
202+
assert.equal(path.posix.extname({}), '');
169203

170204

171205
// path.join tests
@@ -486,8 +520,14 @@ assert.equal(path.posix.delimiter, ':');
486520

487521

488522
// path._makeLong tests
523+
const emptyObj = {};
489524
assert.equal(path.posix._makeLong('/foo/bar'), '/foo/bar');
490525
assert.equal(path.posix._makeLong('foo/bar'), 'foo/bar');
526+
assert.equal(path.posix._makeLong(null), null);
527+
assert.equal(path.posix._makeLong(true), true);
528+
assert.equal(path.posix._makeLong(1), 1);
529+
assert.equal(path.posix._makeLong(), undefined);
530+
assert.equal(path.posix._makeLong(emptyObj), emptyObj);
491531
if (common.isWindows) {
492532
// These tests cause resolve() to insert the cwd, so we cannot test them from
493533
// non-Windows platforms (easily)
@@ -505,6 +545,11 @@ assert.equal(path.win32._makeLong('C:/foo'), '\\\\?\\C:\\foo');
505545
assert.equal(path.win32._makeLong('\\\\foo\\bar'), '\\\\?\\UNC\\foo\\bar\\');
506546
assert.equal(path.win32._makeLong('//foo//bar'), '\\\\?\\UNC\\foo\\bar\\');
507547
assert.equal(path.win32._makeLong('\\\\?\\foo'), '\\\\?\\foo');
548+
assert.equal(path.win32._makeLong(null), null);
549+
assert.equal(path.win32._makeLong(true), true);
550+
assert.equal(path.win32._makeLong(1), 1);
551+
assert.equal(path.win32._makeLong(), undefined);
552+
assert.equal(path.win32._makeLong(emptyObj), emptyObj);
508553

509554

510555
if (common.isWindows)

0 commit comments

Comments
 (0)