aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorWarner Losh <imp@FreeBSD.org>2022-07-28 04:24:50 +0000
committerWarner Losh <imp@FreeBSD.org>2022-07-28 04:29:27 +0000
commit3a1b966ae0c1b9f334e1e3a7ad8b4bf8e845f3c5 (patch)
tree1356f3ab79e5e3aea03221809958df4b736b511a
parent065cbc77076ec8d38385406deefa8331bc2432f5 (diff)
downloadsrc-3a1b966ae0c1b9f334e1e3a7ad8b4bf8e845f3c5.tar.gz
src-3a1b966ae0c1b9f334e1e3a7ad8b4bf8e845f3c5.zip
kboot: Convert from getdents to getdents64
Linux 2.4 introduced getdents64. Switch to using it because aarch64 doesn't have getdents as that syscall was obsoleted before that port was created. Sponsored by: Netflix
-rw-r--r--stand/kboot/arch/amd64/syscall_nr.h2
-rw-r--r--stand/kboot/arch/powerpc64/syscall_nr.h2
-rw-r--r--stand/kboot/host_syscall.h21
-rw-r--r--stand/kboot/host_syscalls.c4
-rw-r--r--stand/kboot/kbootfdt.c18
5 files changed, 29 insertions, 18 deletions
diff --git a/stand/kboot/arch/amd64/syscall_nr.h b/stand/kboot/arch/amd64/syscall_nr.h
index 4d8db2083ebc..71930001c1cf 100644
--- a/stand/kboot/arch/amd64/syscall_nr.h
+++ b/stand/kboot/arch/amd64/syscall_nr.h
@@ -1,6 +1,6 @@
#define SYS_close 3
#define SYS_dup 32
-#define SYS_getdents 78
+#define SYS_getdents64 217
#define SYS_getpid 39
#define SYS_gettimeofday 96
#define SYS_kexec_load 246
diff --git a/stand/kboot/arch/powerpc64/syscall_nr.h b/stand/kboot/arch/powerpc64/syscall_nr.h
index a467259e8b60..0702673c7228 100644
--- a/stand/kboot/arch/powerpc64/syscall_nr.h
+++ b/stand/kboot/arch/powerpc64/syscall_nr.h
@@ -1,7 +1,7 @@
#define SYS_close 6
#define SYS_dup 41
#define SYS_fstat 108
-#define SYS_getdents 141
+#define SYS_getdents64 202
#define SYS_getpid 20
#define SYS_gettimeofday 78
#define SYS_kexec_load 268
diff --git a/stand/kboot/host_syscall.h b/stand/kboot/host_syscall.h
index b867cd9f0d99..9f876952641e 100644
--- a/stand/kboot/host_syscall.h
+++ b/stand/kboot/host_syscall.h
@@ -131,13 +131,32 @@ struct host_kexec_segment {
int memsz;
};
+struct host_dirent64 {
+ uint64_t d_ino; /* 64-bit inode number */
+ int64_t d_off; /* 64-bit offset to next structure */
+ unsigned short d_reclen; /* Size of this dirent */
+ unsigned char d_type; /* File type */
+ char d_name[]; /* Filename (null-terminated) */
+};
+
+/* d_type values */
+#define HOST_DT_UNKNOWN 0
+#define HOST_DT_FIFO 1
+#define HOST_DT_CHR 2
+#define HOST_DT_DIR 4
+#define HOST_DT_BLK 6
+#define HOST_DT_REG 8
+#define HOST_DT_LNK 10
+#define HOST_DT_SOCK 12
+#define HOST_DT_WHT 14
+
/*
* System Calls
*/
int host_close(int fd);
int host_dup(int fd);
int host_fstat(int fd, struct host_kstat *sb);
-int host_getdents(int fd, void *dirp, int count);
+int host_getdents64(int fd, void *dirp, int count);
int host_getpid(void);
int host_gettimeofday(struct host_timeval *a, void *b);
int host_kexec_load(unsigned long entry, unsigned long nsegs, struct host_kexec_segment *segs, unsigned long flags);
diff --git a/stand/kboot/host_syscalls.c b/stand/kboot/host_syscalls.c
index 865107263d7b..771f9e128fdd 100644
--- a/stand/kboot/host_syscalls.c
+++ b/stand/kboot/host_syscalls.c
@@ -26,9 +26,9 @@ host_fstat(int fd, struct host_kstat *sb)
}
int
-host_getdents(int fd, void *dirp, int count)
+host_getdents64(int fd, void *dirp, int count)
{
- return host_syscall(SYS_getdents, fd, (uintptr_t)dirp, count);
+ return host_syscall(SYS_getdents64, fd, (uintptr_t)dirp, count);
}
int
diff --git a/stand/kboot/kbootfdt.c b/stand/kboot/kbootfdt.c
index 5e0ef9ea3068..e4e8e7cfbf04 100644
--- a/stand/kboot/kbootfdt.c
+++ b/stand/kboot/kbootfdt.c
@@ -40,30 +40,23 @@ add_node_to_fdt(void *buffer, const char *path, int fdt_offset)
void *propbuf;
ssize_t proplen;
- struct host_dent {
- unsigned long d_fileno;
- unsigned long d_off;
- unsigned short d_reclen;
- char d_name[];
- /* uint8_t d_type; */
- };
char dents[2048];
- struct host_dent *dent;
+ struct host_dirent64 *dent;
int d_type;
fd = host_open(path, O_RDONLY, 0);
while (1) {
- dentsize = host_getdents(fd, dents, sizeof(dents));
+ dentsize = host_getdents64(fd, dents, sizeof(dents));
if (dentsize <= 0)
break;
- for (dent = (struct host_dent *)dents;
+ for (dent = (struct host_dirent64 *)dents;
(char *)dent < dents + dentsize;
- dent = (struct host_dent *)((void *)dent + dent->d_reclen)) {
+ dent = (struct host_dirent64 *)((void *)dent + dent->d_reclen)) {
sprintf(subpath, "%s/%s", path, dent->d_name);
if (strcmp(dent->d_name, ".") == 0 ||
strcmp(dent->d_name, "..") == 0)
continue;
- d_type = *((char *)(dent) + dent->d_reclen - 1);
+ d_type = dent->d_type;
if (d_type == 4 /* DT_DIR */) {
child_offset = fdt_add_subnode(buffer, fdt_offset,
dent->d_name);
@@ -72,7 +65,6 @@ add_node_to_fdt(void *buffer, const char *path, int fdt_offset)
child_offset, path, dent->d_name);
continue;
}
-
add_node_to_fdt(buffer, subpath, child_offset);
} else {
propbuf = malloc(1024);