|
@ -210,3 +210,47 @@ if (!fs.lutimes) { |
|
|
fs.lutimesSync = function () {} |
|
|
fs.lutimesSync = function () {} |
|
|
} |
|
|
} |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// https://github.com/isaacs/node-graceful-fs/issues/4
|
|
|
|
|
|
// Chown should not fail on einval or eperm if non-root.
|
|
|
|
|
|
|
|
|
|
|
|
fs.chown = chownFix(fs.chown) |
|
|
|
|
|
fs.fchown = chownFix(fs.fchown) |
|
|
|
|
|
fs.lchown = chownFix(fs.lchown) |
|
|
|
|
|
|
|
|
|
|
|
fs.chownSync = chownFixSync(fs.chownSync) |
|
|
|
|
|
fs.fchownSync = chownFixSync(fs.fchownSync) |
|
|
|
|
|
fs.lchownSync = chownFixSync(fs.lchownSync) |
|
|
|
|
|
|
|
|
|
|
|
function chownFix (orig) { |
|
|
|
|
|
if (!orig) return orig |
|
|
|
|
|
return function (target, uid, gid, cb) { |
|
|
|
|
|
return orig.call(fs, target, uid, gid, function (er, res) { |
|
|
|
|
|
if (chownErOk(er)) er = null |
|
|
|
|
|
cb(er, res) |
|
|
|
|
|
}) |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
function chownFixSync (orig) { |
|
|
|
|
|
if (!orig) return orig |
|
|
|
|
|
return function (target, uid, gid) { |
|
|
|
|
|
try { |
|
|
|
|
|
return orig.call(fs, target, uid, gid) |
|
|
|
|
|
} catch (er) { |
|
|
|
|
|
if (!chownErOk(er)) throw er |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
function chownErOk (er) { |
|
|
|
|
|
// if there's no getuid, or if getuid() is something other than 0,
|
|
|
|
|
|
// and the error is EINVAL or EPERM, then just ignore it.
|
|
|
|
|
|
// This specific case is a silent failure in cp, install, tar,
|
|
|
|
|
|
// and most other unix tools that manage permissions.
|
|
|
|
|
|
// When running as root, or if other types of errors are encountered,
|
|
|
|
|
|
// then it's strict.
|
|
|
|
|
|
if (!er || (!process.getuid || process.getuid() !== 0) |
|
|
|
|
|
&& (er.code === "EINVAL" || er.code === "EPERM")) return true |
|
|
|
|
|
} |
|
|