1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-24 21:07:34 +00:00

Kernel: Don't include null terminator in sys$readlink() result

POSIX says, "Conforming applications should not assume that the returned
contents of the symbolic link are null-terminated."

If we do include the null terminator into the returning string, Python
believes it to actually be a part of the returned name, and gets unhappy
about that later. This suggests other systems Python runs in don't include
it, so let's do that too.

Also, make our userspace support non-null-terminated realpath().
This commit is contained in:
Sergey Bugaev 2020-04-14 18:39:56 +03:00 committed by Andreas Kling
parent 1dee4d0049
commit f18d6610d3
3 changed files with 11 additions and 8 deletions

View file

@ -108,10 +108,11 @@ PropertiesDialog::PropertiesDialog(GUI::FileSystemModel& model, String path, boo
if (S_ISLNK(m_mode)) { if (S_ISLNK(m_mode)) {
char link_destination[PATH_MAX]; char link_destination[PATH_MAX];
if (readlink(path.characters(), link_destination, sizeof(link_destination)) < 0) { ssize_t len = readlink(path.characters(), link_destination, sizeof(link_destination));
if (len < 0) {
perror("readlink"); perror("readlink");
} else { } else {
properties.append({ "Link target:", link_destination }); properties.append({ "Link target:", String(link_destination, len) });
} }
} }

View file

@ -1950,10 +1950,10 @@ int Process::sys$readlink(const Syscall::SC_readlink_params* user_params)
return -EIO; // FIXME: Get a more detailed error from VFS. return -EIO; // FIXME: Get a more detailed error from VFS.
auto link_target = String::copy(contents); auto link_target = String::copy(contents);
if (link_target.length() + 1 > params.buffer.size) if (link_target.length() > params.buffer.size)
return -ENAMETOOLONG; return -ENAMETOOLONG;
copy_to_user(params.buffer.data, link_target.characters(), link_target.length() + 1); copy_to_user(params.buffer.data, link_target.characters(), link_target.length());
return link_target.length() + 1; return link_target.length();
} }
int Process::sys$chdir(const char* user_path, size_t path_length) int Process::sys$chdir(const char* user_path, size_t path_length)

View file

@ -176,11 +176,13 @@ size_t print_name(const struct stat& st, const String& name, const char* path_fo
if (S_ISLNK(st.st_mode)) { if (S_ISLNK(st.st_mode)) {
if (path_for_link_resolution) { if (path_for_link_resolution) {
char linkbuf[PATH_MAX]; char linkbuf[PATH_MAX];
ssize_t nread = readlink(path_for_link_resolution, linkbuf, sizeof(linkbuf)); ssize_t nread = readlink(path_for_link_resolution, linkbuf, sizeof(linkbuf) - 1);
if (nread < 0) if (nread < 0) {
perror("readlink failed"); perror("readlink failed");
else } else {
linkbuf[nread] = '\0';
nprinted += printf(" -> ") + print_escaped(linkbuf); nprinted += printf(" -> ") + print_escaped(linkbuf);
}
} else { } else {
nprinted += printf("@"); nprinted += printf("@");
} }