fix(libkernel): reject empty filesystem paths
This commit is contained in:
parent
0f863c1022
commit
d26c9bcabc
|
|
@ -226,6 +226,7 @@ int APS5_VABI sceKernelStat(const char* path, FileStat* sb) {
|
|||
if (sb == nullptr) {
|
||||
throw std::invalid_argument(std::string(__func__) + ": sb is null");
|
||||
}
|
||||
if (*path == '\0') return SceErrorFromErrno(2);
|
||||
std::filesystem::path native;
|
||||
try {
|
||||
native = ResolvePath_nid_no_patch(path);
|
||||
|
|
@ -249,6 +250,7 @@ int APS5_VABI sceKernelUnlink(const char* path) {
|
|||
if (path == nullptr) {
|
||||
throw std::invalid_argument(std::string(__func__) + ": path is null");
|
||||
}
|
||||
if (*path == '\0') return SceErrorFromErrno(2);
|
||||
auto native = ResolvePath_nid_no_patch(path);
|
||||
constexpr int GuestEperm = 1;
|
||||
std::error_code error;
|
||||
|
|
|
|||
|
|
@ -696,6 +696,7 @@ int APS5_VABI unlink_nid_postfix(const char* path) {
|
|||
|
||||
int APS5_VABI sceKernelCheckReachability(const char* path) {
|
||||
if (path == nullptr) return SCE_KERNEL_ERROR_EINVAL;
|
||||
if (*path == '\0') return SCE_KERNEL_ERROR_ENOENT;
|
||||
if (std::strlen(path) > 255) return SCE_KERNEL_ERROR_ENAMETOOLONG;
|
||||
std::error_code error;
|
||||
return std::filesystem::exists(ResolvePath_nid_no_patch(path), error) ? 0 : SCE_KERNEL_ERROR_ENOENT;
|
||||
|
|
@ -999,6 +1000,7 @@ int64_t APS5_VABI pwritev_nid_postfix(int d, const KernelIovec* iov, int iovcnt,
|
|||
|
||||
int APS5_VABI sceKernelRename(const char* from, const char* to) {
|
||||
if (from == nullptr || to == nullptr) throw std::invalid_argument("sceKernelRename: path is null");
|
||||
if (*from == '\0' || *to == '\0') return SceErrorFromErrno(GUEST_ENOENT);
|
||||
const auto source = ResolvePath_nid_no_patch(from);
|
||||
std::error_code error;
|
||||
if (!std::filesystem::exists(source, error)) return SceErrorFromErrno(GUEST_ENOENT);
|
||||
|
|
@ -1012,6 +1014,7 @@ int APS5_VABI sceKernelRename(const char* from, const char* to) {
|
|||
|
||||
int APS5_VABI sceKernelRmdir(const char* path) {
|
||||
if (path == nullptr) throw std::invalid_argument("sceKernelRmdir: path is null");
|
||||
if (*path == '\0') return SceErrorFromErrno(GUEST_ENOENT);
|
||||
const auto native = ResolvePath_nid_no_patch(path);
|
||||
std::error_code error;
|
||||
if (!std::filesystem::is_directory(native, error)) {
|
||||
|
|
@ -1035,6 +1038,7 @@ extern "C" {
|
|||
|
||||
int APS5_VABI sceKernelChmod_nid_postfix(const char* path, std::uint16_t mode) {
|
||||
if (!path) return SceErrorFromErrno(GUEST_EFAULT);
|
||||
if (!*path) return SceErrorFromErrno(GUEST_ENOENT);
|
||||
const auto native = ResolvePath_nid_no_patch(path);
|
||||
if (NativeChmod(native, mode & 07777) != 0) return SceErrorFromErrno(errno);
|
||||
return 0;
|
||||
|
|
@ -1052,6 +1056,7 @@ int APS5_VABI fchmod_nid_postfix(int d, int mode) {
|
|||
|
||||
int APS5_VABI sceKernelTruncate_nid_postfix(const char* path, std::int64_t length) {
|
||||
if (path == nullptr) throw std::invalid_argument("sceKernelTruncate: path is null");
|
||||
if (*path == '\0') return SceErrorFromErrno(GUEST_ENOENT);
|
||||
if (length < 0) return SceErrorFromErrno(GUEST_EINVAL);
|
||||
const auto native = ResolvePath_nid_no_patch(path);
|
||||
std::error_code error;
|
||||
|
|
@ -1070,6 +1075,7 @@ int APS5_VABI truncate_nid_postfix(const char* path, std::int64_t length) {
|
|||
|
||||
int APS5_VABI sceKernelUtimes_nid_postfix(const char* path, const KernelTimeval* times) {
|
||||
if (path == nullptr) throw std::invalid_argument("sceKernelUtimes: path is null");
|
||||
if (*path == '\0') return SceErrorFromErrno(GUEST_ENOENT);
|
||||
if (times != nullptr) {
|
||||
for (int i = 0; i < 2; ++i) {
|
||||
if (times[i].tv_usec < 0 || times[i].tv_usec >= 1000000) return SCE_KERNEL_ERROR_EINVAL;
|
||||
|
|
|
|||
|
|
@ -45,8 +45,10 @@ int APS5_VABI mkdir_nid_postfix(const char*, unsigned short);
|
|||
int APS5_VABI sceKernelOpen(const char*, int, unsigned short);
|
||||
int APS5_VABI sceKernelClose(int);
|
||||
int APS5_VABI sceKernelStat(const char*, FileStat*);
|
||||
int APS5_VABI sceKernelCheckReachability(const char*);
|
||||
int APS5_VABI sceKernelFstat(int, FileStat*);
|
||||
int APS5_VABI sceKernelUnlink(const char*);
|
||||
int APS5_VABI sceKernelRename(const char*, const char*);
|
||||
int APS5_VABI sceKernelRmdir(const char*);
|
||||
int APS5_VABI sceKernelMkdir(const char*, unsigned short);
|
||||
int* APS5_VABI __error_nid_postfix();
|
||||
|
|
@ -77,6 +79,7 @@ static void Check(bool value, int line) {
|
|||
int main() {
|
||||
Require(chmod_nid_postfix(nullptr, 0600) == -1 && *__error_nid_postfix() == 14);
|
||||
Require(sceKernelChmod_nid_postfix(nullptr, 0600) == static_cast<int>(0x8002000eu));
|
||||
Require(chmod_nid_postfix("", 0600) == -1 && *__error_nid_postfix() == 2);
|
||||
Require(chmod_nid_postfix("anyps5_missing_chmod_path", 0600) == -1 && *__error_nid_postfix() == 2);
|
||||
Require(sceKernelChmod_nid_postfix("anyps5_missing_chmod_path", 0600) == static_cast<int>(0x80020002u));
|
||||
Require(sceKernelDebugOutText(-1, "text") == static_cast<int>(0x80020016u));
|
||||
|
|
@ -267,6 +270,21 @@ int main() {
|
|||
const auto rootName = root.string();
|
||||
{ std::ofstream stream(present); stream << "posix"; }
|
||||
FileStat status{};
|
||||
Require(sceKernelStat("", &status) == static_cast<int>(0x80020002u));
|
||||
Require(sceKernelCheckReachability("") == static_cast<int>(0x80020002u));
|
||||
Require(sceKernelRename("", presentName.c_str()) == static_cast<int>(0x80020002u));
|
||||
Require(sceKernelRename(presentName.c_str(), "") == static_cast<int>(0x80020002u));
|
||||
Require(sceKernelRmdir("") == static_cast<int>(0x80020002u));
|
||||
Require(sceKernelMkdir("", 0700) == static_cast<int>(0x80020002u));
|
||||
const auto cwdPermissions = std::filesystem::status(".").permissions();
|
||||
Require(sceKernelChmod_nid_postfix("", static_cast<unsigned short>(cwdPermissions) & 07777) == static_cast<int>(0x80020002u));
|
||||
Require(sceKernelTruncate_nid_postfix("", 0) == static_cast<int>(0x80020002u));
|
||||
const auto cwdWriteTime = std::filesystem::last_write_time(".");
|
||||
const int emptyUtimes = sceKernelUtimes_nid_postfix("", nullptr);
|
||||
std::error_code restoreTimeError;
|
||||
std::filesystem::last_write_time(".", cwdWriteTime, restoreTimeError);
|
||||
Require(!restoreTimeError);
|
||||
Require(emptyUtimes == static_cast<int>(0x80020002u));
|
||||
Require(stat_nid_postfix(presentName.c_str(), &status) == 0 && status.st_size == 5);
|
||||
Require(stat_nid_postfix(missingName.c_str(), &status) == -1 && *__error_nid_postfix() == 2);
|
||||
Require(sceKernelStat(missingName.c_str(), &status) == static_cast<int>(0x80020002u));
|
||||
|
|
@ -478,6 +496,7 @@ int main() {
|
|||
Require(rmdir_nid_postfix(nullptr) == -1 && *__error_nid_postfix() == 14);
|
||||
Require(unlink_nid_postfix(missingName.c_str()) == -1 && *__error_nid_postfix() == 2);
|
||||
Require(sceKernelUnlink(missingName.c_str()) == static_cast<int>(0x80020002u));
|
||||
Require(sceKernelUnlink("") == static_cast<int>(0x80020002u));
|
||||
Require(unlink_nid_postfix("") == -1 && *__error_nid_postfix() == 2);
|
||||
Require(unlink_nid_postfix(nullptr) == -1 && *__error_nid_postfix() == 14);
|
||||
Require(unlink_nid_postfix(rootName.c_str()) == -1 && *__error_nid_postfix() == 1 && std::filesystem::is_directory(root));
|
||||
|
|
|
|||
Loading…
Reference in New Issue