mirror of
https://github.com/fish-shell/fish-shell
synced 2024-11-11 15:37:24 +00:00
make wreaddir()
handle broken struct dirent
Some platforms do not correctly define `struct dirent` so that its
`d_name` member is long enough for the longest file name. Work around
such broken definitions.
Fixes #4030
(cherry picked from commit a5a9ca7d3b
)
This commit is contained in:
parent
c9c802d3fc
commit
40679560a6
1 changed files with 10 additions and 3 deletions
|
@ -87,15 +87,22 @@ bool wreaddir_resolving(DIR *dir, const wcstring &dir_path, wcstring &out_name,
|
||||||
}
|
}
|
||||||
|
|
||||||
bool wreaddir(DIR *dir, wcstring &out_name) {
|
bool wreaddir(DIR *dir, wcstring &out_name) {
|
||||||
struct dirent d;
|
// We need to use a union to ensure that the dirent struct is large enough to avoid stomping on
|
||||||
|
// the stack. Some platforms incorrectly defined the `d_name[]` member as being one element
|
||||||
|
// long when it should be at least NAME_MAX + 1.
|
||||||
|
union {
|
||||||
|
struct dirent d;
|
||||||
|
char c[offsetof(struct dirent, d_name) + NAME_MAX + 1]; /* NAME_MAX is POSIX. */
|
||||||
|
} d_u;
|
||||||
struct dirent *result = NULL;
|
struct dirent *result = NULL;
|
||||||
int retval = readdir_r(dir, &d, &result);
|
|
||||||
|
|
||||||
|
int retval = readdir_r(dir, &d_u.d, &result);
|
||||||
if (retval || !result) {
|
if (retval || !result) {
|
||||||
out_name = L"";
|
out_name = L"";
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
out_name = str2wcstring(d.d_name);
|
|
||||||
|
out_name = str2wcstring(d_u.d.d_name);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue