Set the Critical Error number immediately after calling a device driver.

This solves problems with int24 handlers that call int21/ah=59.
Let truename and blockrw return with an error if there is a critical error.
Don't overwrite the critical error # with the DOS error #.


git-svn-id: https://svn.code.sf.net/p/freedos/svn/kernel/trunk@709 6ac86273-5f31-0410-b378-82cca8765d1b
This commit is contained in:
Bart Oldeman 2003-09-24 19:34:11 +00:00
parent 6df5c0be61
commit bdc5569995
8 changed files with 30 additions and 24 deletions

View File

@ -462,7 +462,7 @@ ddt * getddt(int dev);
/* error.c */
COUNT char_error(request * rq, struct dhdr FAR * lpDevice);
COUNT block_error(request * rq, COUNT nDrive, struct dhdr FAR * lpDevice);
COUNT block_error(request * rq, COUNT nDrive, struct dhdr FAR * lpDevice, int mode);
/* sysclk.c */
WORD ASMCFUNC FAR clk_driver(rqptr rp);

View File

@ -446,7 +446,7 @@ UWORD dskxfer(COUNT dsk, ULONG blkno, VOID FAR * buf, UWORD numblocks,
return (IoReqHdr.r_status);
loop:
switch (block_error(&IoReqHdr, dpbp->dpb_unit, dpbp->dpb_device))
switch (block_error(&IoReqHdr, dpbp->dpb_unit, dpbp->dpb_device, mode))
{
case ABORT:
case FAIL:

View File

@ -306,8 +306,9 @@ long DosRWSft(int sft_idx, size_t n, void FAR * bp, int mode)
}
/* /// End of additions for SHARE - Ron Cemer */
{
UCOUNT XferCount;
XferCount = rwblock(s->sft_status, bp, n, mode);
long XferCount = rwblock(s->sft_status, bp, n, mode);
if (XferCount < 0)
return XferCount;
if (mode == XFR_WRITE)
s->sft_size = dos_getfsize(s->sft_status);
s->sft_posit += XferCount;

View File

@ -78,14 +78,18 @@ VOID fatal(BYTE * err_msg)
/* Abort, retry or fail for character devices */
COUNT char_error(request * rq, struct dhdr FAR * lpDevice)
{
CritErrCode = (rq->r_status & S_MASK) + 0x13;
return CriticalError(EFLG_CHAR | EFLG_ABORT | EFLG_RETRY | EFLG_IGNORE,
0, rq->r_status & S_MASK, lpDevice);
}
/* Abort, retry or fail for block devices */
COUNT block_error(request * rq, COUNT nDrive, struct dhdr FAR * lpDevice)
COUNT block_error(request * rq, COUNT nDrive, struct dhdr FAR * lpDevice,
int mode)
{
return CriticalError(EFLG_ABORT | EFLG_RETRY | EFLG_IGNORE,
CritErrCode = (rq->r_status & S_MASK) + 0x13;
return CriticalError(EFLG_ABORT | EFLG_RETRY | EFLG_IGNORE |
(mode == DSKWRITE ? EFLG_WRITE : 0),
nDrive, rq->r_status & S_MASK, lpDevice);
}

View File

@ -1537,7 +1537,7 @@ STATIC COUNT dos_extend(f_node_ptr fnp)
/* Read/write block from disk */
/* checking for valid access was already done by the functions in
dosfns.c */
UCOUNT rwblock(COUNT fd, VOID FAR * buffer, UCOUNT count, int mode)
long rwblock(COUNT fd, VOID FAR * buffer, UCOUNT count, int mode)
{
REG f_node_ptr fnp;
REG struct buffer FAR *bp;
@ -1714,7 +1714,7 @@ UCOUNT rwblock(COUNT fd, VOID FAR * buffer, UCOUNT count, int mode)
mode == XFR_READ ? DSKREAD : DSKWRITE))
{
fnp->f_offset = startoffset;
return ret_cnt;
return DE_ACCESS;
}
goto update_pointers;
@ -2080,7 +2080,7 @@ COUNT media_check(REG struct dpb FAR * dpbp)
|| !(MediaReqHdr.r_status & S_DONE))
{
loop1:
switch (block_error(&MediaReqHdr, dpbp->dpb_unit, dpbp->dpb_device))
switch (block_error(&MediaReqHdr, dpbp->dpb_unit, dpbp->dpb_device, 0))
{
case ABORT:
case FAIL:
@ -2129,7 +2129,7 @@ COUNT media_check(REG struct dpb FAR * dpbp)
{
loop2:
switch (block_error
(&MediaReqHdr, dpbp->dpb_unit, dpbp->dpb_device))
(&MediaReqHdr, dpbp->dpb_unit, dpbp->dpb_device, 0))
{
case ABORT:
case FAIL:

View File

@ -400,8 +400,14 @@ dispatch:
}
#endif
if ((lr.AH >= 0x38 && lr.AH <= 0x4F) || (lr.AH >= 0x56 && lr.AH <= 0x5c))
if ((lr.AH >= 0x38 && lr.AH <= 0x4F) || (lr.AH >= 0x56 && lr.AH <= 0x5c) ||
(lr.AH >= 0x5e && lr.AH <= 0x60) || (lr.AH >= 0x65 && lr.AH <= 0x6a) ||
lr.AH == 0x6c)
{
CLEAR_CARRY_FLAG();
if (lr.AH != 0x59)
CritErrCode = SUCCESS;
}
/* Clear carry by default for these functions */
@ -1328,12 +1334,12 @@ dispatch:
CLEAR_CARRY_FLAG();
break;
default:
CritErrCode = SUCCESS;
goto error_invalid;
}
break;
case 0x5e:
CLEAR_CARRY_FLAG();
switch (lr.AL)
{
case 0x00:
@ -1355,7 +1361,6 @@ dispatch:
break;
case 0x5f:
CLEAR_CARRY_FLAG();
if (lr.AL == 7 || lr.AL == 8)
{
struct cds FAR *cdsp;
@ -1400,7 +1405,6 @@ dispatch:
break;
case 0x60: /* TRUENAME */
CLEAR_CARRY_FLAG();
if ((rc = DosTruename(MK_FP(lr.DS, lr.SI), adjust_far(FP_ES_DI))) < SUCCESS)
goto error_exit;
break;
@ -1490,12 +1494,10 @@ dispatch:
break;
}
CLEAR_CARRY_FLAG();
break;
/* Code Page functions */
case 0x66:
CLEAR_CARRY_FLAG();
switch (lr.AL)
{
case 1:
@ -1514,7 +1516,6 @@ dispatch:
/* Set Max file handle count */
case 0x67:
CLEAR_CARRY_FLAG();
if ((rc = SetJFTSize(lr.BX)) != SUCCESS)
goto error_exit;
break;
@ -1522,14 +1523,12 @@ dispatch:
/* Flush file buffer -- COMMIT FILE. */
case 0x68:
case 0x6a:
CLEAR_CARRY_FLAG();
if ((rc = DosCommit(lr.BX)) < 0)
goto error_exit;
break;
/* Get/Set Serial Number */
case 0x69:
CLEAR_CARRY_FLAG();
rc = (lr.BL == 0 ? default_drive : lr.BL - 1);
if (lr.AL == 0 || lr.AL == 1)
{
@ -1560,8 +1559,7 @@ dispatch:
case 0x6c:
{
long lrc;
CLEAR_CARRY_FLAG();
if (lr.AL != 0 ||
(lr.DL & 0x0f) > 0x2 || (lr.DL & 0xf0) > 0x10)
goto error_invalid;
@ -1588,6 +1586,7 @@ dispatch:
/* DOS 7.0+ FAT32 extended functions */
case 0x73:
CLEAR_CARRY_FLAG();
CritErrCode = SUCCESS;
rc = int21_fat32(&lr);
if (rc != SUCCESS)
goto error_exit;
@ -1640,7 +1639,8 @@ error_invalid:
rc = DE_INVLDFUNC;
error_exit:
lr.AX = -rc;
CritErrCode = lr.AX; /* Maybe set */
if (CritErrCode == SUCCESS)
CritErrCode = lr.AX; /* Maybe set */
error_carry:
SET_CARRY_FLAG();
exit_dispatch:

View File

@ -449,7 +449,8 @@ COUNT truename(const char FAR * src, char * dest, COUNT mode)
*p = '\\'; /* force backslash! */
}
p++;
DosGetCuDir((UBYTE)((result & 0x1f) + 1), p);
if (DosGetCuDir((UBYTE)((result & 0x1f) + 1), p) < 0)
return DE_PATHNOTFND;
if (*src != '\\' && *src != '/')
p += strlen(p);
else /* skip the absolute path marker */

View File

@ -162,7 +162,7 @@ BOOL dos_setfsize(COUNT fd, LONG size);
COUNT dos_mkdir(BYTE * dir);
BOOL last_link(f_node_ptr fnp);
COUNT map_cluster(REG f_node_ptr fnp, COUNT mode);
UCOUNT rwblock(COUNT fd, VOID FAR * buffer, UCOUNT count, int mode);
long rwblock(COUNT fd, VOID FAR * buffer, UCOUNT count, int mode);
COUNT dos_read(COUNT fd, VOID FAR * buffer, UCOUNT count);
COUNT dos_write(COUNT fd, const VOID FAR * buffer, UCOUNT count);
LONG dos_lseek(COUNT fd, LONG foffset, COUNT origin);