mirror of
https://github.com/RGBCube/serenity
synced 2025-07-24 16:47:42 +00:00
UserspaceEmulator: Add syscalls: stat(), realpath(), gethostname()
This is enough to run /bin/ls :^)
This commit is contained in:
parent
9def88e08d
commit
b8d3dbcf2d
2 changed files with 57 additions and 0 deletions
|
@ -245,6 +245,12 @@ u32 Emulator::virt_syscall(u32 function, u32 arg1, u32 arg2, u32 arg3)
|
||||||
switch (function) {
|
switch (function) {
|
||||||
case SC_execve:
|
case SC_execve:
|
||||||
return virt$execve(arg1);
|
return virt$execve(arg1);
|
||||||
|
case SC_stat:
|
||||||
|
return virt$stat(arg1);
|
||||||
|
case SC_realpath:
|
||||||
|
return virt$realpath(arg1);
|
||||||
|
case SC_gethostname:
|
||||||
|
return virt$gethostname(arg1, arg2);
|
||||||
case SC_ioctl:
|
case SC_ioctl:
|
||||||
return virt$ioctl(arg1, arg2, arg3);
|
return virt$ioctl(arg1, arg2, arg3);
|
||||||
case SC_get_dir_entries:
|
case SC_get_dir_entries:
|
||||||
|
@ -927,4 +933,52 @@ int Emulator::virt$execve(FlatPtr params_addr)
|
||||||
return execve(argv[0], (char* const*)argv.data(), (char* const*)envp.data());
|
return execve(argv[0], (char* const*)argv.data(), (char* const*)envp.data());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int Emulator::virt$stat(FlatPtr params_addr)
|
||||||
|
{
|
||||||
|
Syscall::SC_stat_params params;
|
||||||
|
mmu().copy_from_vm(¶ms, params_addr, sizeof(params));
|
||||||
|
|
||||||
|
auto path = String::copy(mmu().copy_buffer_from_vm((FlatPtr)params.path.characters, params.path.length));
|
||||||
|
struct stat host_statbuf;
|
||||||
|
int rc;
|
||||||
|
if (params.follow_symlinks)
|
||||||
|
rc = stat(path.characters(), &host_statbuf);
|
||||||
|
else
|
||||||
|
rc = lstat(path.characters(), &host_statbuf);
|
||||||
|
if (rc < 0)
|
||||||
|
return -errno;
|
||||||
|
mmu().copy_to_vm((FlatPtr)params.statbuf, &host_statbuf, sizeof(host_statbuf));
|
||||||
|
return rc;
|
||||||
|
}
|
||||||
|
|
||||||
|
int Emulator::virt$realpath(FlatPtr params_addr)
|
||||||
|
{
|
||||||
|
Syscall::SC_realpath_params params;
|
||||||
|
mmu().copy_from_vm(¶ms, params_addr, sizeof(params));
|
||||||
|
|
||||||
|
auto path = String::copy(mmu().copy_buffer_from_vm((FlatPtr)params.path.characters, params.path.length));
|
||||||
|
char host_buffer[PATH_MAX] = {};
|
||||||
|
|
||||||
|
Syscall::SC_realpath_params host_params;
|
||||||
|
host_params.path = { path.characters(), path.length() };
|
||||||
|
host_params.buffer = { host_buffer, sizeof(host_buffer) };
|
||||||
|
int rc = syscall(SC_realpath, &host_params);
|
||||||
|
if (rc < 0)
|
||||||
|
return rc;
|
||||||
|
mmu().copy_to_vm((FlatPtr)params.buffer.data, host_buffer, min(params.buffer.size, sizeof(host_buffer)));
|
||||||
|
return rc;
|
||||||
|
}
|
||||||
|
|
||||||
|
int Emulator::virt$gethostname(FlatPtr buffer, ssize_t buffer_size)
|
||||||
|
{
|
||||||
|
if (buffer_size < 0)
|
||||||
|
return -EINVAL;
|
||||||
|
auto host_buffer = ByteBuffer::create_zeroed(buffer_size);
|
||||||
|
int rc = syscall(SC_gethostname, host_buffer.data(), host_buffer.size());
|
||||||
|
if (rc < 0)
|
||||||
|
return rc;
|
||||||
|
mmu().copy_to_vm(buffer, host_buffer.data(), host_buffer.size());
|
||||||
|
return rc;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -74,6 +74,9 @@ private:
|
||||||
int virt$execve(FlatPtr);
|
int virt$execve(FlatPtr);
|
||||||
int virt$get_dir_entries(int fd, FlatPtr buffer, ssize_t);
|
int virt$get_dir_entries(int fd, FlatPtr buffer, ssize_t);
|
||||||
int virt$ioctl(int fd, unsigned, FlatPtr);
|
int virt$ioctl(int fd, unsigned, FlatPtr);
|
||||||
|
int virt$stat(FlatPtr);
|
||||||
|
int virt$realpath(FlatPtr);
|
||||||
|
int virt$gethostname(FlatPtr, ssize_t);
|
||||||
int virt$usleep(useconds_t);
|
int virt$usleep(useconds_t);
|
||||||
int virt$shbuf_create(int size, FlatPtr buffer);
|
int virt$shbuf_create(int size, FlatPtr buffer);
|
||||||
int virt$shbuf_allow_pid(int, pid_t peer_pid);
|
int virt$shbuf_allow_pid(int, pid_t peer_pid);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue