diff options
author | Richard Henderson <richard.henderson@linaro.org> | 2022-04-28 12:04:44 -0700 |
---|---|---|
committer | Richard Henderson <richard.henderson@linaro.org> | 2022-06-28 04:35:52 +0530 |
commit | 9a89470449a5171eb1bd06f681361e0888d15cf7 (patch) | |
tree | b7b7537fe55caf844a34969fc229ded15d46998e /semihosting/arm-compat-semi.c | |
parent | 40f1219a8b2f95808ed5a18798dbce1b57fef211 (diff) |
semihosting: Split out semihost_sys_lseek
Split out the non-ARM specific portions of SYS_SEEK to a
reusable function. This handles all GuestFD. Isolate the
curious ARM-specific return value processing to a new
callback, common_semi_seek_cb.
Expand the internal type of the offset to int64_t, and
provide the whence argument, which will be required by
m68k and nios2 semihosting.
Note that gdb_do_syscall %x reads target_ulong, not int.
Reviewed-by: Luc Michel <lmichel@kalray.eu>
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
Diffstat (limited to 'semihosting/arm-compat-semi.c')
-rw-r--r-- | semihosting/arm-compat-semi.c | 51 |
1 files changed, 13 insertions, 38 deletions
diff --git a/semihosting/arm-compat-semi.c b/semihosting/arm-compat-semi.c index d591fcd7c2..a117d180bc 100644 --- a/semihosting/arm-compat-semi.c +++ b/semihosting/arm-compat-semi.c @@ -224,16 +224,6 @@ static void common_semi_cb(CPUState *cs, target_ulong ret, target_ulong err) #else syscall_err = err; #endif - } else { - /* Fixup syscalls that use nonstardard return conventions. */ - target_ulong reg0 = common_semi_arg(cs, 0); - switch (reg0) { - case TARGET_SYS_SEEK: - ret = 0; - break; - default: - break; - } } common_semi_set_ret(cs, ret); } @@ -258,6 +248,18 @@ static void common_semi_rw_cb(CPUState *cs, target_ulong ret, target_ulong err) } /* + * SYS_SEEK returns 0 on success, not the resulting offset. + */ +static void common_semi_seek_cb(CPUState *cs, target_ulong ret, + target_ulong err) +{ + if (!err) { + ret = 0; + } + common_semi_cb(cs, ret, err); +} + +/* * Return an address in target memory of 64 bytes where the remote * gdb should write its stat struct. (The format of this structure * is defined by GDB's remote protocol and is not target-specific.) @@ -290,7 +292,6 @@ common_semi_flen_cb(CPUState *cs, target_ulong ret, target_ulong err) * via common_semi_cb. */ typedef void sys_isattyfn(CPUState *cs, GuestFD *gf); -typedef void sys_seekfn(CPUState *cs, GuestFD *gf, target_ulong offset); typedef void sys_flenfn(CPUState *cs, GuestFD *gf); static void host_isattyfn(CPUState *cs, GuestFD *gf) @@ -298,12 +299,6 @@ static void host_isattyfn(CPUState *cs, GuestFD *gf) common_semi_cb(cs, isatty(gf->hostfd), 0); } -static void host_seekfn(CPUState *cs, GuestFD *gf, target_ulong offset) -{ - off_t ret = lseek(gf->hostfd, offset, SEEK_SET); - common_semi_cb(cs, ret, ret == -1 ? errno : 0); -} - static void host_flenfn(CPUState *cs, GuestFD *gf) { struct stat buf; @@ -320,11 +315,6 @@ static void gdb_isattyfn(CPUState *cs, GuestFD *gf) gdb_do_syscall(common_semi_cb, "isatty,%x", gf->hostfd); } -static void gdb_seekfn(CPUState *cs, GuestFD *gf, target_ulong offset) -{ - gdb_do_syscall(common_semi_cb, "lseek,%x,%x,0", gf->hostfd, offset); -} - static void gdb_flenfn(CPUState *cs, GuestFD *gf) { gdb_do_syscall(common_semi_flen_cb, "fstat,%x,%x", @@ -353,12 +343,6 @@ static void staticfile_isattyfn(CPUState *cs, GuestFD *gf) common_semi_cb(cs, 0, 0); } -static void staticfile_seekfn(CPUState *cs, GuestFD *gf, target_ulong offset) -{ - gf->staticfile.off = offset; - common_semi_cb(cs, 0, 0); -} - static void staticfile_flenfn(CPUState *cs, GuestFD *gf) { common_semi_cb(cs, gf->staticfile.len, 0); @@ -366,24 +350,20 @@ static void staticfile_flenfn(CPUState *cs, GuestFD *gf) typedef struct GuestFDFunctions { sys_isattyfn *isattyfn; - sys_seekfn *seekfn; sys_flenfn *flenfn; } GuestFDFunctions; static const GuestFDFunctions guestfd_fns[] = { [GuestFDHost] = { .isattyfn = host_isattyfn, - .seekfn = host_seekfn, .flenfn = host_flenfn, }, [GuestFDGDB] = { .isattyfn = gdb_isattyfn, - .seekfn = gdb_seekfn, .flenfn = gdb_flenfn, }, [GuestFDStatic] = { .isattyfn = staticfile_isattyfn, - .seekfn = staticfile_seekfn, .flenfn = staticfile_flenfn, }, }; @@ -520,12 +500,7 @@ void do_common_semihosting(CPUState *cs) case TARGET_SYS_SEEK: GET_ARG(0); GET_ARG(1); - - gf = get_guestfd(arg0); - if (!gf) { - goto do_badf; - } - guestfd_fns[gf->type].seekfn(cs, gf, arg1); + semihost_sys_lseek(cs, common_semi_seek_cb, arg0, arg1, GDB_SEEK_SET); break; case TARGET_SYS_FLEN: |