Files
AnyPS5/core/libs/tests/GuestCharacter.cpp
T
JJenkxandClaude Opus 5.5 1f206b59c4 fix(libc): accept any setlocale category and only the C locale, as titles' libc.prx does
setlocale returned a null pointer for a category outside 0 to 6 and
accepted "POSIX" as a name for "C". The libc.prx that titles ship
ignores the category, so setlocale(-1, NULL) and setlocale(7, "C")
return "C", and returns a null pointer for "POSIX" as for any name other
than "C" or the empty string.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
2026-10-22 20:36:58 -04:00

66 lines
3.2 KiB
C++

#include "prx/libc/include/general/VabiMacros.hpp"
#include <array>
#include <cctype>
#include <clocale>
#include <cstdio>
#include <cstdlib>
#include <cstring>
extern "C" {
int APS5_VABI isupper_nid_postfix(int);
int APS5_VABI islower_nid_postfix(int);
int APS5_VABI isalpha_nid_postfix(int);
int APS5_VABI isdigit_nid_postfix(int);
int APS5_VABI isalnum_nid_postfix(int);
int APS5_VABI isspace_nid_postfix(int);
int APS5_VABI isblank_nid_postfix(int);
int APS5_VABI iscntrl_nid_postfix(int);
int APS5_VABI isprint_nid_postfix(int);
int APS5_VABI isgraph_nid_postfix(int);
int APS5_VABI ispunct_nid_postfix(int);
int APS5_VABI isxdigit_nid_postfix(int);
int APS5_VABI toupper_nid_postfix(int);
int APS5_VABI tolower_nid_postfix(int);
const short* APS5_VABI _Getptolower_nid_postfix();
const short* APS5_VABI _Getptoupper_nid_postfix();
const char* APS5_VABI setlocale_nid_postfix(int, const char*);
}
static void Require(bool value) { if (!value) std::abort(); }
int main() {
Require(std::setlocale(LC_CTYPE, "C") != nullptr);
for (int category = 0; category <= 6; ++category) {
const char* result = setlocale_nid_postfix(category, "C");
Require(result != nullptr && std::strcmp(result, "C") == 0);
Require(setlocale_nid_postfix(category, "POSIX") == nullptr);
result = setlocale_nid_postfix(category, nullptr);
Require(result != nullptr && std::strcmp(result, "C") == 0);
result = setlocale_nid_postfix(category, "");
Require(result != nullptr && std::strcmp(result, "C") == 0);
Require(setlocale_nid_postfix(category, "en_US.UTF-8") == nullptr);
}
for (const int category : std::array<int, 4>{-1, 7, 100, 1 << 30}) {
const char* result = setlocale_nid_postfix(category, "C");
Require(result != nullptr && std::strcmp(result, "C") == 0);
result = setlocale_nid_postfix(category, nullptr);
Require(result != nullptr && std::strcmp(result, "C") == 0);
Require(setlocale_nid_postfix(category, "POSIX") == nullptr && setlocale_nid_postfix(category, "x") == nullptr);
}
for (int c = EOF; c <= 255; ++c) {
Require(bool(isupper_nid_postfix(c)) == bool(std::isupper(c)));
Require(bool(islower_nid_postfix(c)) == bool(std::islower(c)));
Require(bool(isalpha_nid_postfix(c)) == bool(std::isalpha(c)));
Require(bool(isdigit_nid_postfix(c)) == bool(std::isdigit(c)));
Require(bool(isalnum_nid_postfix(c)) == bool(std::isalnum(c)));
Require(bool(isspace_nid_postfix(c)) == bool(std::isspace(c)));
Require(bool(isblank_nid_postfix(c)) == bool(std::isblank(c)));
Require(bool(iscntrl_nid_postfix(c)) == bool(std::iscntrl(c)));
Require(bool(isprint_nid_postfix(c)) == bool(std::isprint(c)));
Require(bool(isgraph_nid_postfix(c)) == bool(std::isgraph(c)));
Require(bool(ispunct_nid_postfix(c)) == bool(std::ispunct(c)));
Require(bool(isxdigit_nid_postfix(c)) == bool(std::isxdigit(c)));
Require(toupper_nid_postfix(c) == std::toupper(c));
Require(tolower_nid_postfix(c) == std::tolower(c));
Require(toupper_nid_postfix(c) == _Getptoupper_nid_postfix()[c]);
Require(tolower_nid_postfix(c) == _Getptolower_nid_postfix()[c]);
}
}