From aaf3ef695b12a88ab99986749dc2cf3672d6994e Mon Sep 17 00:00:00 2001 From: Tee-Kiah Chia Date: Wed, 24 Mar 2021 14:30:18 +0000 Subject: [PATCH] plat/msdos86: implement close( ) function & proper errno setting --- plat/msdos86/libsys/close.s | 23 +++++++++++++++ plat/msdos86/libsys/errno.s | 28 +++++++++++++++++++ plat/msdos86/libsys/sys_seterrno.c | 45 ++++++++++++++++++++++++++++++ plat/msdos86/libsys/sys_xret.s | 35 +++++++++++++++++++++++ 4 files changed, 131 insertions(+) create mode 100644 plat/msdos86/libsys/close.s create mode 100644 plat/msdos86/libsys/errno.s create mode 100644 plat/msdos86/libsys/sys_seterrno.c create mode 100644 plat/msdos86/libsys/sys_xret.s diff --git a/plat/msdos86/libsys/close.s b/plat/msdos86/libsys/close.s new file mode 100644 index 000000000..b8c2f8a15 --- /dev/null +++ b/plat/msdos86/libsys/close.s @@ -0,0 +1,23 @@ +# +! $Source$ +! $State$ +! $Revision$ + +! Declare segments (the order is important). + +.sect .text +.sect .rom +.sect .data +.sect .bss + +.sect .text + +! Close a file. + +.define _close +_close: + mov bx, sp + mov bx, 2(bx) + movb ah, 0x3E + int 0x21 + jmp .sys_zret diff --git a/plat/msdos86/libsys/errno.s b/plat/msdos86/libsys/errno.s new file mode 100644 index 000000000..9858d2640 --- /dev/null +++ b/plat/msdos86/libsys/errno.s @@ -0,0 +1,28 @@ +# +! $Source$ +! $State$ +! $Revision$ + +! Declare segments (the order is important). + +.sect .text +.sect .rom +.sect .data +.sect .bss + +#define D(e) .define e; e + +.sect .data + +! Define various ACK error numbers. Note that these are *not* ANSI C +! errnos, and are used for different purposes. + +D(ERANGE) = 1 +D(ESET) = 2 +D(EIDIVZ) = 6 +D(EHEAP) = 17 +D(EILLINS) = 18 +D(EODDZ) = 19 +D(ECASE) = 20 +D(EBADMON) = 25 + diff --git a/plat/msdos86/libsys/sys_seterrno.c b/plat/msdos86/libsys/sys_seterrno.c new file mode 100644 index 000000000..779e600f5 --- /dev/null +++ b/plat/msdos86/libsys/sys_seterrno.c @@ -0,0 +1,45 @@ +/* $Source$ + * $State$ + * $Revision$ + */ + +#include + +static const signed char err_map[] = + { + 0, /* 0x00 no error */ + EINVAL, /* 0x01 function number invalid */ + ENOENT, /* 0x02 file not found */ + ENOENT, /* 0x03 path not found */ + EMFILE, /* 0x04 too many open files */ + EACCES, /* 0x05 access denied */ + EBADF, /* 0x06 invalid handle */ + EFAULT, /* 0x07 mem. control block destroyed */ + ENOMEM, /* 0x08 insufficient memory */ + EFAULT, /* 0x09 memory block address invalid */ + E2BIG, /* 0x0A environment invalid */ + ENOEXEC, /* 0x0B format invalid */ + EINVAL, /* 0x0C access code invalid */ + EINVAL, /* 0x0D data invalid */ + ENOEXEC, /* 0x0E (?) fixup overflow */ + ENODEV, /* 0x0F invalid drive */ + EBUSY, /* 0x10 attempt to remove curr. dir. */ + EXDEV, /* 0x11 not same device */ + ENOENT, /* 0x12 no more files */ + EIO, /* 0x13 disk write-protected */ + EIO, /* 0x14 unknown unit */ + ENXIO, /* 0x15 drive not ready */ + }; + +/* + * Map an MS-DOS 2+ system error code to an `errno' value and store that in + * `errno'. Return -1. + */ +int _sys_seterrno(unsigned dos_err) +{ + if (dos_err < sizeof(err_map) / sizeof(err_map[0])) + errno = err_map[dos_err]; + else + errno = EIO; + return -1; +} diff --git a/plat/msdos86/libsys/sys_xret.s b/plat/msdos86/libsys/sys_xret.s new file mode 100644 index 000000000..a5b65116a --- /dev/null +++ b/plat/msdos86/libsys/sys_xret.s @@ -0,0 +1,35 @@ +# +! $Source$ +! $State$ +! $Revision$ + +! Declare segments (the order is important). + +.sect .text +.sect .rom +.sect .data +.sect .bss + +.sect .text + +! .sys_zret: if the carry flag is set, then set `errno' from the DOS error +! code in ax, and return -1. If the carry flag is clear, just return zero. +! +! .sys_axret: if the carry flag is set, then set `errno' from the DOS error +! code in ax, and return -1. If the carry flag is clear, just return ax as +! a return value. + +.extern .sys_zret +.extern .sys_axret +.sys_zret: + jc error + xor ax, ax +no_error: + ret +.sys_axret: + jnc no_error +error: + push ax + call __sys_seterrno + pop cx + ret