1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-06-01 02:28:12 +00:00

Userland: Unveil /usr/lib/Loader.so when using 'x' permissions on unveil

We should not rely on the Kernel to unveil this for us, so if a program
needs to execute another program it should unveil the dynamic loader too
to prevent crashing.
To do this, we check if the user program tried to unveil a binary with
at least using the 'x' permission, so we will try to also unveil the
dynamic loader too.
This commit is contained in:
Liav A 2022-10-24 17:59:56 +03:00 committed by Andrew Kaster
parent 30dc304429
commit d102ea5f81

View file

@ -81,10 +81,34 @@ ErrorOr<void> pledge(StringView promises, StringView execpromises)
HANDLE_SYSCALL_RETURN_VALUE("pledge", rc, {});
}
static ErrorOr<void> unveil_dynamic_loader()
{
static bool dynamic_loader_unveiled { false };
if (dynamic_loader_unveiled)
return {};
// FIXME: Try to find a way to not hardcode the dynamic loader path.
constexpr auto dynamic_loader_path = "/usr/lib/Loader.so"sv;
constexpr auto dynamic_loader_permissions = "x"sv;
Syscall::SC_unveil_params params {
{ dynamic_loader_path.characters_without_null_termination(), dynamic_loader_path.length() },
{ dynamic_loader_permissions.characters_without_null_termination(), dynamic_loader_permissions.length() },
};
int rc = syscall(SC_unveil, &params);
if (rc < 0) {
return Error::from_syscall("unveil (DynamicLoader @ /usr/lib/Loader.so)"sv, rc);
}
dynamic_loader_unveiled = true;
return {};
}
ErrorOr<void> unveil(StringView path, StringView permissions)
{
auto const parsed_path = TRY(Core::SessionManagement::parse_path_with_sid(path));
if (permissions.contains('x'))
TRY(unveil_dynamic_loader());
Syscall::SC_unveil_params params {
{ parsed_path.characters(), parsed_path.length() },
{ permissions.characters_without_null_termination(), permissions.length() },