MZ is back!

This commit is contained in:
Mark Zbikowski 2024-04-25 21:24:10 +01:00
parent 8ee9712c74
commit 656c98b804
1259 changed files with 519749 additions and 4 deletions

View File

@ -1,10 +1,11 @@
<img width="150" height="150" align="left" style="float: left; margin: 0 10px 0 0;" alt="MS-DOS logo" src="https://github.com/Microsoft/MS-DOS/blob/main/.readmes/msdos-logo.png">
<img width="150" height="150" align="left" style="float: left; margin: 0 10px 0 0;" alt="MS-DOS logo" src="https://github.com/Microsoft/MS-DOS/blob/main/msdos-logo.png">
# MS-DOS v1.25 and v2.0 Source Code
# MS-DOS v1.25, v2.0, v4.0 Source Code
This repo contains the original source-code and compiled binaries for MS-DOS v1.25 and MS-DOS v2.0.
This repo contains the original source-code and compiled binaries for MS-DOS v1.25 and MS-DOS v2.0, plus the source-code for MS-DOS v4.00 jointly developed by IBM and
Microsoft.
These are the same files [originally shared at the Computer History Museum on March 25th, 2014]( http://www.computerhistory.org/atchm/microsoft-ms-dos-early-source-code/) and are being (re)published in this repo to make them easier to find, reference-to in external writing and works, and to allow exploration and experimentation for those interested in early PC Operating Systems.
The MS-DOS v1.25 and v2.0 files [were originally shared at the Computer History Museum on March 25th, 2014]( http://www.computerhistory.org/atchm/microsoft-ms-dos-early-source-code/) and are being (re)published in this repo to make them easier to find, reference-to in external writing and works, and to allow exploration and experimentation for those interested in early PC Operating Systems.
# License

21
v4.0/LICENSE Normal file
View File

@ -0,0 +1,21 @@
MIT License
Copyright (c) IBM and Microsoft Corporation.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE

103
v4.0/src/BIOS/BIOSTRUC.INC Normal file
View File

@ -0,0 +1,103 @@
%OUT BIOSTRUC.INC...
; SCCSID = @(#)BIOSTRUC.INC 1.0 86/09/30
; ROM BIOS CALL PACKET STRUCTURES
;*******************************
;System Service call ( Int 15h )
;*******************************
;Function AH = 0C0h, Return system configuration
;For PC and PCJR on return:
; (AH) = 80h
; (CY) = 1
;For PCXT, PC PORTABLE and PCAT on return:
; (AH) = 86h
; (CY) = 1
;For all others:
; (AH) = 0
; (CY) = 0
; (ES:BX) = pointer to system descriptor vector in ROS
; System descriptor :
; DW xxxx length of descriptor in bytes,
; minimum length = 8
; DB xx model byte
; 0FFh = PC
; 0FEh = PC/XT, Portable
; 0FDh = PC/JR
; 0FCh = PC/AT, 6Mhz PC/AT,
; 6Mhz PC/AT running coprocessor(?),
; PS/2 Model 50, 50 z
; 0FAh = PS/2 Model 25, 30
; 0F9h = PC Convertible
; 0F8h = PS/2 Model 80
; 0F7h = Nova
; 0E0 thru 0EFh = reserved
;
; DB xx secondary model byte
; 000h = PC1
; 000h = PC/XT, Portable
; 000h = PC/JR
; 000h = PC/AT
; 001h = 6Mhz PC/AT
; 003h = 6Mhz PC/AT running coprocessor(?)
; 004h = PS/2 Model 50, 50z
; 001h = PS/2 Model 25
; 000h = PC Convertible
; 000h = PS/2 Model 80
; 000h = Nova
;
; DB xx bios revision level
; 00 for first release, subsequent release
; of code with same model byte and
; secondary model byte require revison level
; to increase by one.
;
; DB xx feature information byte 1
; X0000000 = 1, bios use DMA channel 3
; = 0, DMA channel 3 not used
;
; 0X000000 = 1, 2nd Interrupt chip present
; = 0, 2nd Interrupt chip not present
;
; 00X00000 = 1, Real Time Clock present
; = 0, Real Time Clock not present
;
; 000X0000 = 1, Keyboard escape sequence(INT15h)
; called in keyboard interrupt
; (Int 09h).
; = 0, Keyboard escape sequence not
; called.
; 0000XXXX reserved
;
; DB xx feature information byte 2 - reserved
;
; DB xx feature information byte 2 - reserved
;
; DB xx feature information byte 2 - reserved
;
; DB xx feature information byte 2 - reserved
;
BIOS_SYSTEM_DESCRIPTOR struc
bios_SD_leng dw ?
bios_SD_modelbyte db ?
bios_SD_scnd_modelbyte db ?
db ?
bios_SD_featurebyte1 db ?
db 4 dup (?)
BIOS_SYSTEM_DESCRIPTOR ends
;FeatureByte1 bit map equates
DMAchannel3 equ 10000000b
ScndIntController equ 01000000b
RealTimeClock equ 00100000b
KeyEscapeSeq equ 00010000b
;
;Model Byte
MDL_PC1 EQU 0FFH
MDL_XT EQU 0FEH
MDL_JR EQU 0FDH
MDL_AT EQU 0FCH
MDL_CONVERT EQU 0F9H
mdl_ps2_30 equ 0fah
mdl_ps2_80 equ 0f8h

View File

@ -0,0 +1,78 @@
;
; date_verify loosely checks bcd date values to be in range in bin_date_time
;
date_verify: ;
assume ds:code,es:nothing
cmp byte ptr bin_date_time+0,20h ; century check
ja date_error ; jmp error
jz century_20 ; jmp in 20th century
cmp byte ptr bin_date_time+0,19h ; century check
jb date_error ; jmp error
cmp byte ptr bin_date_time+1,80h ; year check
jb date_error ; jmp error
century_20: ;
cmp byte ptr bin_date_time+1,99h ; year check
ja date_error ; jmp error
cmp byte ptr bin_date_time+2,12h ; month check
ja date_error ; jmp error
cmp byte ptr bin_date_time+2,00h ; month check
jbe date_error ; jmp error
cmp byte ptr bin_date_time+3,31h ; day check
ja date_error ; jmp error
cmp byte ptr bin_date_time+3,00h ; day check
jbe date_error ; jmp error
clc ; set success flag
ret ;
date_error: ;
stc ; set error flag
ret ;
;
; time_verify very loosely checks bcd date values to be in range in bin_date_time
;
time_verify:
assume ds:code,es:nothing
cmp byte ptr bin_date_time+0,24H
ja time_error
cmp byte ptr bin_date_time+1,59H
ja time_error
cmp byte ptr bin_date_time+2,59H
ja time_error
clc
ret
time_error:
stc
ret
;
; bcd_verify checks values in bin_date_time to be valid
; bcd numerals. carry set if any nibble out of range
;
bcd_verify: ;
assume ds:code,es:nothing
mov cx,4 ; 4 bytes to check
mov bx,offset bin_date_time ;
bv_loop: ;
mov al,[bx] ; get a bcd number (0..99)
mov ah,al ;
and ax,0f00fh ; 10's place in high ah, 1's in al
cmp al,10 ; is 1's place in range?
ja bv_error ; jmp out of range
shr ah,1 ; swap nibbles
shr ah,1 ; ...
shr ah,1 ; ...
shr ah,1 ; ...
and ah,0fh ; get rid of any erroneous bits
cmp ah,10 ; is 10's place in range
ja bv_error ; jmp out of range
inc bx ; next byte
dec cx ;
jnz bv_loop ;
clc ; set success flag
ret ;
bv_error: ;
stc ; set error flag
ret ;
;
; Dos 3.30 - The real time clock structures were moved to msbio2.asm
;

50
v4.0/src/BIOS/CMOSEQU.INC Normal file
View File

@ -0,0 +1,50 @@
;;Rev 3.30 Modification
;Equates for CMOS.
;----------------------------------------
; CMOS EQUATES FOR THIS SYSTEM :
;-------------------------------------------------------------------------------
CMOS_PORT EQU 070H ; I/O ADDRESS OF CMOS ADDRESS PORT
CMOS_DATA EQU 071H ; I/O ADDRESS OF CMOS DATA PORT
NMI EQU 10000000B ; DISABLE NMI INTERRUPTS MASK -
; HIGH BIT OF CMOS LOCATION ADDRESS
;---------- CMOS TABLE LOCATION ADDRESS'S ## -----------------------------------
CMOS_SECONDS EQU 000H ; SECONDS
CMOS_SEC_ALARM EQU 001H ; SECONDS ALARM ## NOTE: ALL LOCATIONS
CMOS_MINUTES EQU 002H ; MINUTES | IN THE CMOS AREA
CMOS_MIN_ALARM EQU 003H ; MINUTES ALARM | ARE IBM USE ONLY
CMOS_HOURS EQU 004H ; HOURS | AND SUBJECT TO
CMOS_HR_ALARM EQU 005H ; HOURS ALARM | CHANGE. ONLY THE
CMOS_DAY_WEEK EQU 006H ; DAY OF THE WEEK | POST & BIOS CODE
CMOS_DAY_MONTH EQU 007H ; DAY OF THE MONTH | SHOULD DIRECTLY
CMOS_MONTH EQU 008H ; MONTH | ACCESS LOCATIONS
CMOS_YEAR EQU 009H ; YEAR (TWO DIGITS) | IN CMOS STORAGE.
CMOS_REG_A EQU 00AH ; STATUS REGISTER A '-----------------
CMOS_REG_B EQU 00BH ; STATUS REGISTER B ALARM
CMOS_REG_C EQU 00CH ; STATUS REGISTER C FLAGS
CMOS_REG_D EQU 00DH ; STATUS REGISTER D BATTERY
CMOS_DIAG EQU 00EH ; POST DIAGNOSTIC STATUS RESULTS BYTE
CMOS_SHUT_DOWN EQU 00FH ; SHUTDOWN STATUS COMMAND BYTE
CMOS_DISKETTE EQU 010H ; DISKETTE DRIVE TYPE BYTE ;
; EQU 011H ; - RESERVED ;C
CMOS_DISK EQU 012H ; FIXED DISK TYPE BYTE ;H
; EQU 013H ; - RESERVED ;E
CMOS_EQUIP EQU 014H ; EQUIPMENT WORD LOW BYTE ;C
CMOS_B_M_S_LO EQU 015H ; BASE MEMORY SIZE - LOW BYTE (X1024) ;K
CMOS_B_M_S_HI EQU 016H ; BASE MEMORY SIZE - HIGH BYTE ;S
CMOS_E_M_S_LO EQU 017H ; EXPANSION MEMORY SIZE - LOW BYTE ;U
CMOS_E_M_S_HI EQU 018H ; EXPANSION MEMORY SIZE - HIGH BYTE ;M
CMOS_DISK_1 EQU 019H ; FIXED DISK TYPE - DRIVE C EXTENSION ;E
CMOS_DISK_2 EQU 01AH ; FIXED DISK TYPE - DRIVE D EXTENSION ;D
; EQU 01BH ; - 1BH THROUGH 2DH - RESERVED ;
CMOS_CKSUM_HI EQU 02EH ; CMOS CHECKSUM - HIGH BYTE ;*
CMOS_CKSUM_LO EQU 02FH ; CMOS CHECKSUM - LOW BYTE ;*
CMOS_U_M_S_LO EQU 030H ; USABLE MEMORY ABOVE 1 MEG - LOW BYTE
CMOS_U_M_S_HI EQU 031H ; USABLE MEMORY ABOVE 1 MEG - HIGH BYTE
CMOS_CENTURY EQU 032H ; DATE CENTURY BYTE (BCD)
CMOS_INFO128 EQU 033H ; 128KB INFORMATION STATUS FLAG BYTE
; EQU 034H ; - 34H THROUGH 3FH - RESERVED
;
;;End of Modification


33
v4.0/src/BIOS/DEFEMS.INC Normal file
View File

@ -0,0 +1,33 @@
;J.K. This is a temporary version of EMS function definitions needed for
;IBMBIO SYSINIT.
EMS_INT equ 67h ;interrupt vector designated for EMS.
EMS_STATUS equ 40h ;status of memery manager
EQ_PAGES equ 42h ;get number of unallocated & total pages
E_GET_HANDLE equ 43h ;allocate pages
EMAP_L_TO_P equ 44h ;Map logical to physical page
EMAP_STATE equ 4Fh ;Mapping status
GET_MAP_STATE equ 00h
GET_MAP_SIZE equ 02h
SET_MAP_STATE equ 01h
EDE_ALLOCATE equ 45h ;deallocate pages
EMS_VERSION equ 46h ;Get EMM version number
GET_PAGE_FRAME equ 58h ;Get page frame address
GET_PAGEFRAME_TAB equ 00H
GET_NUM_PAGEFRAME equ 01H
EMS_HANDLE_NAME equ 53h
SET_HANDLE_NAME equ 01h
IBM_PAGE_ID equ 255 ;Physical page id that will be used by
;IBMBIO and IBMDOS for buffer manipulation.
;MAX_NUM_PAGEFRAME equ 12 ;maximum number of page frames IBMBIO can
;handle
MAX_NUM_PAGEFRAME equ 64 ;maximum number of page frames MSBIO can
;handle
EMSVERSION equ 40h ;4.0


23
v4.0/src/BIOS/DEVMARK.INC Normal file
View File

@ -0,0 +1,23 @@
;Structure, Equtes for DEVMARK for MEM command.
DEVMARK struc
DEVMARK_ID db 0
DEVMARK_SEG dw 0
DEVMARK_SIZE dw 0
DEVMARK_DUM db 3 dup (?)
DEVMARK_FILENAME db 8 dup (' ')
DEVMARK ends
DEVMARK_STK equ 'S'
DEVMARK_DEVICE equ 'D'
DEVMARK_IFS equ 'I'
DEVMARK_BUF equ 'B'
DEVMARK_CDS equ 'L' ;lastdrive
DEVMARK_FILES equ 'F'
DEVMARK_FCBS equ 'X'
DEVMARK_INST equ 'T' ;used for SYSINIT BASE for INSTALL= command.
DEVMARK_EMS_STUB equ 'E'
SETBRKDONE equ 00000001b
FOR_DEVMARK equ 00000010b
NOT_FOR_DEVMARK equ 11111101b

31
v4.0/src/BIOS/JUMPMAC.INC Normal file
View File

@ -0,0 +1,31 @@
;;Rev 3.30 Modification
;
; given a label <lbl> either 2 byte jump to another label <lbl>_J
; if it is near enough or 3 byte jump to <lbl>
;
jump macro lbl
local a
.xcref
ifndef lbl&_j ;; is this the first invocation
a:
JMP lbl
ELSE
IF (lbl&_J GE $) OR ($-lbl&_J GT 126)
a:
JMP lbl ;; is the jump too far away?
ELSE
a:
JMP lbl&_J ;; do the short one...
ENDIF
ENDIF
lbl&_j = a
.cref
endm
.xcref jump
;REDEFINE THE ABOVE MACRO TO ALWAYS TRY A 3 BYTE NEAR JUMP
JUMP MACRO LBL
JMP LBL
ENDM ;;End of Modification


1
v4.0/src/BIOS/LOCSCR Normal file
View File

@ -0,0 +1 @@
70

167
v4.0/src/BIOS/MAKEFILE Normal file
View File

@ -0,0 +1,167 @@
#************************** makefile for bios ***************************
dest =io
msg =..\messages
dos =..\dos
inc =..\inc
hinc =..\h
#
####################### dependencies begin here. #########################
#
all: $(dest).sys
msbio.cl1: msbio.skl \
$(msg)\$(COUNTRY).msg
msload.obj: msload.asm \
makefile \
msbio.cl1 \
$(inc)\bootform.inc \
$(inc)\versiona.inc \
msload.inc
msload.com: msload.obj
link msload.obj,msload,,;
exe2bin msload.exe msload.com
msbio1.obj: msbio1.asm \
makefile \
msbdata.inc \
msgroup.inc \
jumpmac.inc \
pushpop.inc \
$(inc)\devsym.inc \
msdskpr.inc \
msmacro.inc
mscon.obj: mscon.asm \
makefile \
msgroup.inc \
jumpmac.inc \
msmacro.inc
msaux.obj: msaux.asm \
makefile \
msgroup.inc \
jumpmac.inc \
msmacro.inc
mslpt.obj: mslpt.asm \
makefile \
msgroup.inc \
msequ.inc \
$(inc)\msbds.inc \
msmacro.inc \
$(inc)\devsym.inc \
$(inc)\ioctl.inc $(inc)\bpb.inc
msclock.obj: msclock.asm \
makefile \
msgroup.inc \
msmacro.inc
msdisk.obj: msdisk.asm \
makefile \
msgroup.inc \
msequ.inc \
$(inc)\msbds.inc \
pushpop.inc \
msmacro.inc \
$(inc)\devsym.inc \
msdskpr.inc \
msioctl.inc $(inc)\ioctl.inc $(inc)\bpb.inc
msinit.obj: msinit.asm \
makefile \
msgroup.inc \
msdskpr.inc \
msequ.inc $(inc)\msbds.inc \
$(inc)\cputype.inc \
msmacro.inc \
readcloc.inc \
clocksub.inc \
msextrn.inc
sysinit1.obj: sysinit1.asm \
makefile \
msstack.inc \
msbio.cl4 \
msbio.cl5 \
stkinit.inc \
devmark.inc \
$(inc)\smifssym.inc \
$(inc)\devsym.inc \
$(inc)\ioctl.inc \
$(inc)\cputype.inc \
$(inc)\smdossym.inc $(inc)\dosmac.inc $(inc)\bpb.inc $(inc)\buffer.inc \
$(inc)\sysvar.inc $(inc)\vector.inc $(inc)\dirent.inc \
$(inc)\dpb.inc $(inc)\curdir.inc \
$(inc)\pdb.inc $(inc)\exe.inc $(inc)\sf.inc $(inc)\arena.inc \
$(inc)\intnat.inc $(inc)\mi.inc \
$(inc)\syscall.inc
sysconf.obj: sysconf.asm \
makefile \
psoption.inc \
devmark.inc \
$(inc)\psdata.inc \
$(inc)\parse.asm \
$(inc)\smifssym.inc \
$(inc)\devsym.inc \
$(inc)\ioctl.inc \
$(inc)\smdossym.inc $(inc)\dosmac.inc $(inc)\bpb.inc $(inc)\buffer.inc \
$(inc)\sysvar.inc $(inc)\vector.inc $(inc)\dirent.inc \
$(inc)\dpb.inc $(inc)\curdir.inc \
$(inc)\pdb.inc $(inc)\exe.inc $(inc)\sf.inc $(inc)\arena.inc \
$(inc)\intnat.inc $(inc)\mi.inc \
$(inc)\syscall.inc
sysinit2.obj: sysinit2.asm \
makefile \
devmark.inc \
$(inc)\copyrigh.inc \
$(inc)\smifssym.inc \
$(inc)\devsym.inc \
$(inc)\ioctl.inc \
$(inc)\smdossym.inc $(inc)\dosmac.inc $(inc)\bpb.inc $(inc)\buffer.inc \
$(inc)\sysvar.inc $(inc)\vector.inc $(inc)\dirent.inc \
$(inc)\dpb.inc $(inc)\curdir.inc \
$(inc)\pdb.inc $(inc)\exe.inc $(inc)\sf.inc $(inc)\arena.inc \
$(inc)\intnat.inc $(inc)\mi.inc \
$(inc)\syscall.inc
sysimes.obj: sysimes.asm \
makefile \
msmacro.inc \
msbio.cl3 \
msequ.inc $(inc)\msbds.inc
msbio2.obj: msbio2.asm \
makefile \
msgroup.inc \
msequ.inc \
$(inc)\msbds.inc \
$(inc)\devsym.inc \
pushpop.inc \
msmacro.inc \
msbio.cl2 \
ms96tpi.inc msvolid.inc
mshard.obj: mshard.asm $(inc)\postequ.inc $(inc)\dseg.inc
$(dest).sys: msbio.cl1 msbio1.obj mscon.obj msaux.obj \
mslpt.obj msclock.obj msdisk.obj msbio2.obj \
msinit.obj mshard.obj sysinit1.obj sysconf.obj \
sysinit2.obj sysimes.obj \
msload.com \
makefile
link @msbio.lnk
exe2bin msbio.exe msbio.bin <locscr
copy /b msload.com+msbio.bin $(dest).sys
del msbio.bin
del msbio.exe

536
v4.0/src/BIOS/MS96TPI.INC Normal file
View File

@ -0,0 +1,536 @@
%OUT MS96TPI.INC...
;==============================================================================
;REVISION HISTORY:
;AN000 - New for DOS Version 4.00 - J.K.
;AC000 - Changed for DOS Version 4.00 - J.K.
;AN00x - PTM number for DOS Version 4.00 - J.K.
;==============================================================================
;AN001 - p2781 Changeline error behavior incompatibile with DOS 3.3 1/06/88 J.K.
;==============================================================================
;
; DISK OPEN/CLOSE ROUTINES ARR 2.41
;
DSK$OPEN: ;ARR 2.41
PUBLIC DSK$OPEN
MESSAGE FTESTDISK,<"DISK OPEN ">
MNUM FTESTDISK,AX
MESSAGE FTESTDISK,<CR,LF>
; AL IS LOGICAL DRIVE
CALL SETDRIVE ;GET BDS FOR DRIVE
INC WORD PTR DS:[DI].OPCNT
JMP EXIT ;ARR 2.41
DSK$CLOSE: ;ARR 2.41
PUBLIC DSK$CLOSE
MESSAGE FTESTDISK,<"DISK CLOSE ">
MNUM FTESTDISK,AX
MESSAGE FTESTDISK,<CR,LF>
; AL IS LOGICAL DRIVE
CALL SETDRIVE ;GET BDS FOR DRIVE
CMP WORD PTR DS:[DI].OPCNT,0
JZ EXITJX ; WATCH OUT FOR WRAP ARR 2.41
DEC WORD PTR DS:[DI].OPCNT
EXITJX:
JMP EXIT
; INPUT : DS:DI POINTS TO CURRENT BDS FOR DRIVE.
; RETURN : ZERO SET IF NO OPEN FILES
; ZERO RESET IF OPEN FILES
CHKOPCNT:
MESSAGE FTEST96,<"CHECK OPEN COUNT ">
MNUM FTEST96,AX
MESSAGE FTEST96,<CR,LF>
CMP WORD PTR DS:[DI].OPCNT,0
RET
;
; AT MEDIA CHECK TIME, WE NEED TO REALLY GET DOWN AND CHECK WHAT THE CHANGE IS.
; THIS IS GUARANTEED TO BE EXPENSIVE.
;
PUBLIC MEDIACHECK
MEDIACHECK:
CALL CHECKSINGLE ; MAKE SURE CORRECT DISK IS IN PLACE
XOR SI,SI
CALL HASCHANGE
JZ MEDIARET
CALL CHECKROMCHANGE
JNZ MEDIADOVOLID
PUSH AX
PUSH DX
;SB33001****************************************************************
mov DL, DS:[DI.drivenum] ;SB ; set logical drive number ;3.30*
mov AH, 16h ;SB ; get changeline status ;3.30*
int 13h ;SB ; call rom diskette routine ;3.30*
;SB33001****************************************************************
POP DX
POP AX
JC MEDIADOVOLID
MOV SI,1 ; SIGNAL NO CHANGE
; THERE ARE SOME DRIVES WITH CHANGELINE THAT "LOSE" THE CHANGELINE INDICATION
; IF A DIFFERENT DRIVE IS ACCESSED AFTER THE CURRENT ONE. IN ORDER TO AVOID
; MISSING A MEDIA CHANGE, WE RETURN AN "I DON'T KNOW" TO DOS IF THE CHANGELINE
; IS NOT ACTIVE AND WE ARE ACCESSING A DIFFERENT DRIVE FROM THE LAST ONE.
; IF WE ARE ACCESSING THE SAME DRIVE, THEN WE CAN SAFELY RELY ON THE CHANGELINE
; STATUS.
PUBLIC LOSECHNG
LOSECHNG:
MOV BL,CS:[TIM_DRV] ; GET LAST DRIVE ACCESSED
CMP BYTE PTR [DI].DRIVENUM,BL
JZ MEDIARET
; DO THE 2 SECOND TWIDDLE. IF TIME >= 2 SECONDS, DO A VOLID CHECK.
; OTHERWISE RETURN "I DON'T KNOW" (STRICTLY SPEAKING, WE SHOULD RETURN A
; "NOT CHANGED" HERE SINCE THE 2 SECOND TEST SAID NO CHANGE.) - RS.
SAVEREG <AX,CX,DX>
CALL CHECK_TIME_OF_ACCESS
RESTOREREG <DX,CX,AX>
OR SI,SI
JZ MEDIADOVOLID ; CHECK_TIME SAYS ">= 2 SECS PASSED"
XOR SI,SI ; RETURN "I DON'T KNOW"
PUBLIC MEDIARET
MEDIARET:
RET
;
; SOMEHOW THE MEDIA WAS CHANGED. LOOK AT VID TO SEE. WE DO NOT LOOK AT FAT
; BECAUSE THIS MAY BE DIFFERENT SINCE WE ONLY SET MEDBYT WHEN DOING A READ
; OR WRITE.
;
MEDIADOVOLID:
CALL GETBP ; BUILD A NEW BPB IN CURRENT BDS
JC MEDIARET
CALL CHECK_VID
JNC MEDIARET
CALL MAPERROR ; FIX UP AL FOR RETURN TO DOS
RET
;
; SIMPLE, QUICK CHECK OF LATCHED CHANGE. IF NO INDICATION, THEN RETURN
; OTHERWISE DO EXPENSIVE CHECK. IF THE EXPENSIVE TEST FAILS, POP OFF THE
; RETURN AND SET AL = 15 (FOR INVALID MEDIA CHANGE) WHICH WILL BE RETURNED TO
; DOS.
;J.K. 9/16/86 For DOS 3.3, this will work only for the drive that has
;J.K. 9/16/86 changeline.
PUBLIC CHECKLATCHIO
CHECKLATCHIO:
; IF RETURNING FAKE BPB THEN ASSUME THE DISK HAS NOT CHANGED
; TEST WORD PTR DS:[DI].FLAGS, RETURN_FAKE_BPB
; JNZ CHECKRET
;J.K. 9/16/86
; call HasChange ;change line supported?
; jz CheckRet ;No. Just return
CALL CHKOPCNT
JNZ CHECKROM
CHECKRET:
RET
;
; CHECK FOR PAST ROM INDICATIONS. IF NO ROM CHANGE INDICATED, THEN RETURN OK.
;
PUBLIC CHECKROM
CHECKROM:
CALL CHECKROMCHANGE
JZ CHECKRET ; NO CHANGE
;
; WE NOW SEE THAT A CHANGE LINE HAS BEEN SEEN IN THE PAST. LET'S DO THE
; EXPENSIVE VERIFICATION.
;
MESSAGE FTEST96,<"CHECKROMCHANGE SAYS YES...",CR,LF>
CALL GETBP ; BUILD BPB IN CURRENT BDS
JC RET_NO_ERROR_MAP ; GETBP HAS ALREADY CALLED MAPERROR
CALL CHECK_VID
JC CHECKLATCHRET ; DISK ERROR TRYING TO READ IN.
OR SI,SI ; IS CHANGED FOR SURE?
JNS CHECKRET
CALL RETURNVID
CHECKLATCHRET:
CALL MAPERROR ; FIX UP AL FOR RETURN TO DOS
RET_NO_ERROR_MAP:
STC
POP SI ; POP OFF RETURN ADDRESS
RET
;
; CHECK THE FAT AND THE VID. RETURN IN DI -1 OR 0. RETURN WITH CARRY SET
; ONLY IF THERE WAS A DISK ERROR. RETURN THAT ERROR CODE IN AX.
;
PUBLIC CHECKFATVID
CHECKFATVID:
MESSAGE FTEST96,<"CHECK FAT",CR,LF>
CALL FAT_CHECK
OR SI,SI
JS CHANGED_DRV
;
; THE FAT WAS THE SAME. HOW ABOUT THE VOLUME ID?
;
CHECK_VID:
;J.K. Now with the extended BOOT record, the logic should be enhanced.
;If it is the extended BOOT record, then we check the volume serial
;number instead of volume id. If it is different, then set SI to -1.
;If it is same, then SI= 1 (No change).
;If it is not the extended BOOT record, then just follows the old
;logic. DOS 4.00 will check if the # of FAT in the boot record BPB
;is not 0. If it is 0 then it must be Non_FAT based system and
;should have already covered by extended boot structure checking.
;So, we will return "I don't know" by setting SI to 0.
;This routine assume the newest valid boot record is in CS:[DISKSECTOR].
;(This will be gauranteed by a successful GETBP call right before this
;routine.)
MESSAGE FTEST96,<"CHECK VID",CR,LF>
;SB34MS96TPI001*********************************************************
;SB check the EXT_Boot_Sig variable for the Extended boot signature
;SB if it is set then go to do the extended ID check otherwise continue
;SB with code below
;SB 2 LOCS
cmp cs:[Ext_Boot_Sig],Ext_Boot_Signature
jz Do_Ext_Check_Id
;SB34MS96TPI001*********************************************************
call HasChange ;AN000;
jz CheckRet ;AN000;
xor si,si ;AN000; assume I don't know.
cmp byte ptr cs:[SECPERCLUSINSECTOR]+3,0 ;AN000; Don't read vol id from
je CHECKFATRET ;AN000; the directory if not FAT system
CALL READ_VOLUME_ID
JC CHECKFATRET
CALL CHECK_VOLUME_ID
OR SI,SI
JNZ CHANGED_DRV
MESSAGE FTEST96,<"VID NOT CHANGED",CR,LF>
VID_NO_Changed:
CALL RESETCHANGED
clc ;AN000;
CHECKFATRET:
RET
CHANGED_DRV:
MOV CS:[TIM_DRV],-1 ; ENSURE THAT WE ASK ROM FOR MEDIA
RET ; CHECK NEXT TIME ROUND
;
; extended ID check
;
Do_Ext_Check_ID: ;AN000;
push ax ;AN000;
;SB34MS96TPI002**************************************************************
;SB The code to check extended ID is basically a check to see if the
;Sb volume serial number is still the same. The volume serial number
;SB previously read is in cs:[Boot_Serial_H] and cs:[Boot_Serial_L]
;SB high and low words respectively. DS:DI points to the BDS of the
;SB drive under consideration. The BDS has fields containing the
;SB high and low words of the volume serial number of the media in the
;SB drive. Compare these fields to the fields mentioned above. If these
;SB fields do not match the media has changed and so we should jump
;SB to the code starting at Ext_Changed else return "I don't know" status
;SB in the register used for the changeline status and continue executing
;SB the code given below. For temporary storage use the register which
;SB has been saved and restored around this block.
;SB 7 LOCS
;SB BDS fields in inc\msbds.inc
mov ax,cs:[Boot_Serial_L]
cmp ax,word ptr ds:[di+VOL_SERIAL]
jnz Ext_Changed
mov ax,cs:[Boot_Serial_H]
cmp ax,word ptr ds:[di+VOL_SERIAL+2]
jnz Ext_Changed
xor si,si ; don't know
;SB34MS96TPI002**************************************************************
pop ax ;AN000;
; jmp CheckFatRet ;AN000;
jmp VID_NO_Changed ;AN001;Reset the flag
Ext_Changed: ;AN000; Serial number is different!
pop ax ;AN000;
mov si, -1 ;AN000; disk changed!
clc ;AN000; clear carry. Only SI is meaningful here.
jmp Changed_Drv ;AN000;
;
; AT I/O TIME, WE DETECTED THE ERROR. NOW WE NEED TO DETERMINE WHETHER THE
; MEDIA WAS TRULY CHANGED OR NOT. WE RETURN NORMALLY IF MEDIA CHANGE UNKNOWN.
; AND WE POP OFF THE CALL AND JMP TO HARDERR IF WE SEE AN ERROR.
;
PUBLIC CHECKIO
CHECKIO:
CMP AH,06
JNZ CHECKFATRET
CALL CHKOPCNT
JZ CHECKFATRET ; NO OPEN FILES
; IF RETURNING FAKE BPB THEN IGNORE DISK CHANGES
; TEST WORD PTR DS:[DI].FLAGS, RETURN_FAKE_BPB
; JNZ IGNORECHANGE
CALL GETBP ; BUILD UP A NEW BPB IN CURRENT BDS
JC NO_ERROR_MAP ; GETBP HAS ALREADY CALLED MAPERROR
CALL CHECKFATVID
JC CHECKIORET ; DISK ERROR TRYING TO READ IN.
OR SI,SI ; IS CHANGED FOR SURE?
JS CHECKIOERR ; YES CHANGED
IGNORECHANGE:
INC BP ; ALLOW A RETRY
RET
CHECKIOERR:
CALL RETURNVID
CHECKIORET:
; POP SI ; POP OFF RETURN
STC ; MAKE SURE CARRY GETS PASSED THROUGH
JMP HARDERR
NO_ERROR_MAP:
JMP HARDERR2
;
; RETURN VID SETS UP THE VID FOR A RETURN TO DOS.
;
PUBLIC RETURNVID
RETURNVID:
MESSAGE FTEST96,<"RETURN VID",CR,LF>
PUSH DS ; SAVE POINTER TO CURRENT BDS
PUSH DI
PUSH CX
CALL INIT_VID_LOOP ; SETS ES:DI -> VID
LDS BX,CS:[PTRSAV]
MOV [BX.EXTRA],DI
MOV [BX.EXTRA+2],ES
POP CX
POP DI ; RESTORE CURRENT BDS
POP DS
MOV AH,6 ; INVALID MEDIA CHANGE
STC
RET
;
; MUNGE THE TIME OF LAST SUCCESSFUL ACCESS FOR TWEEKED DRIVES
;
; DON'T NEED ANY MORE
; TWEEKCHECK:
; PUSH AX
; MOV AX,WORD PTR DS:[DI].FLAGS
; TEST AL,FCHANGED_BY_FORMAT
; JZ TWEEKDONE
; MOV CS:[TIM_DRV],-1
; TWEEKDONE:
; POP AX
; RET
;
; DRIVE IS THE LOGICAL DRIVE TO USE
;
; FORMAT_MEDIA_CHECK: ;ARR 2.42
; PUSH AX
; MOV AX,WORD PTR DS:[DI].FLAGS
; TEST AL,FCHANGED_BY_FORMAT
; JZ RETF1 ; MEDIA NOT CHANGED VIA FORMAT
; AND AL,NOT FCHANGED_BY_FORMAT
; MOV WORD PTR [DI].FLAGS,AX ; RESET CHANGED_BY_FORMAT BIT
; MOV SI,-1 ; MEDIA CHANGED VIA FORMAT
; RETF1:
; POP AX
; RET
;
; MOVES THE POINTER TO THE VOLID FOR THE DRIVE INTO THE ORIGINAL REQUEST PACKET
; ON ENTRY, DS:BX POINTS TO THE ORIGINAL PACKET.
; NO ATTEMPT IS MADE TO PRESERVE REGISTERS.
;
MEDIA_SET_VID: ; ARR 2.42
PUBLIC MEDIA_SET_VID
CALL INIT_VID_LOOP ; SETS ES:DI -> VID
LDS BX,CS:[PTRSAV] ; GET POINTER TO PACKET
MOV WORD PTR [BX.TRANS+1],DI
MOV WORD PTR [BX.TRANS+3],ES
RET
;
; HIDENSITY - EXAMINE A DRIVE/MEDIA DESCRIPTOR TO SET THE MEDIA TYPE. IF
; THE MEDIA DESCRIPTOR IS NOT F9 (NOT 96TPI OR 3 1/2), WE RETURN AND LET THE
; CALLER DO THE REST. OTHERWISE, WE POP OFF THE RETURN AND JUMP TO THE TAIL
; OF GETBP. FOR 3.5" MEDIA, WE JUST RETURN.
;
; INPUTS: DS:DI POINT TO CORRECT BDS FOR THIS DRIVE
; AH HAS MEDIA BYTE
;
; OUTPUTS: CARRY CLEAR
; NO REGISTERS MODIFIED
; CARRY SET
; AL = SECTORS/FAT
; BH = NUMBER OF ROOT DIRECTORY ENTRIES
; BL = SECTORS PER TRACK
; CX = NUMBER OF SECTORS
; DH = SECTORS PER ALLOCATION UNIT
; DL = NUMBER OF HEADS
;
HIDENSITY:
PUBLIC HIDENSITY
;
; CHECK FOR CORRECT DRIVE
;
TEST WORD PTR DS:[DI].FLAGS,FCHANGELINE ; IS IT SPECIAL?
JZ DOFLOPPY ; NO, DO NORMAL FLOPPY TEST
;
; WE HAVE A MEDIA BYTE THAT IS PRETTY COMPLEX. EXAMINE DRIVE INFORMATION
; TABLE TO SEE WHAT KIND IT IS.
;
CMP BYTE PTR DS:[DI].FORMFACTOR,FFSMALL; IS IT SINGLE-MEDIA?
JZ DOFLOPPY ; YES, USE FATID...
;
; 96 TPI DRIVE
;
CMP AH,0F9H
JNZ DOFLOPPY
MOV AL,7 ; SEVEN SECTORS / FAT
MOV BX,224*256+0FH ; 224 ROOT DIR ENTRIES & 0F SECTOR MAX
MOV CX,80*15*2 ; 80 TRACKS, 15 SECTORS/TRACK, 2 SIDES
MOV DX,01*256+2 ; SECTORS/ALLOCATION UNIT & HEAD MAX
POPR:
ADD SP,2 ; POP OFF RETURN ADDRESS
JMP HAS1 ; RETURN TO TAIL OF GETBP
DOFLOPPY:
RET
PATHSTART 001,TPI96
;
; CERTAIN BOGUS PROGRAMS AVOID DOS ALTOGETHER AND USE INT 13 DIRECTLY. THESE
; PROGRAMS EVEN RETRY OPERATIONS AND, THUS, WILL IGNORE THE DISK CHANGE LOGIC.
;
; WE HOOK INT 13 AND NOTE ALL ERRORS.
;
ASSUME DS:NOTHING,ES:NOTHING,SS:NOTHING
PUBLIC REAL13
REAL13 DD ?
OLDINT DD ?
DMY DW ?
PATHEND 001,TPI96
PUBLIC INT13
INT13 PROC FAR
POP WORD PTR OLDINT
POP WORD PTR OLDINT+2
POP DMY
MESSAGE FTEST13,<"*">
PUSHF
CALL REAL13 ; SIMULATE ANOTHER INT 13
JC ERR13 ; DID AN ERROR OCCUR?
JMP OLDINT ; NO, RETURN AND POP OFF FLAGS
ERR13:
MESSAGE FTEST13,<"INT 13 ERROR ">
MNUM FTEST13,AX
MESSAGE FTEST13,<CR,LF>
PUSHF ; SAVE STATE
CMP AH,06H ; DID I SEE A CHANGE EVENT?
JZ GOTERR ; YES
B: POPF ; NO, SOME OTHER ERROR, IGNORE IT
JMP OLDINT ; RETURN AND POP OFF FLAGS
GOTERR: OR DL,DL ; IS THIS FOR THE HARD DISK?
JS B ; YES, IGNORE
MOV WORD PTR CS:[FLAGBITS],FCHANGED
CALL SET_CHANGED_DL
JMP B
INT13 ENDP
;
; SET_CHANGED_DL - SETS FLAG BITS ACCORDING TO BITS SET IN [FLAGBITS].
; ESSENTIALLY USED TO INDICATE CHANGELINE, OR FORMAT.
;
; INPUTS: DL CONTAINS PHYSICAL DRIVE NUMBER
; [FLAGBITS] CONTAINS BITS TO SET IN THE FLAG FIELD IN THE BDSS
; OUTPUTS: NONE
; REGISTERS MODIFIED: FLAGS
;
SET_CHANGED_DL:
PUBLIC SET_CHANGED_DL
MESSAGE FTEST96,<"SET CHANGED",CR,LF>
PUSH BX
PUSH DX
MOV BL,DL
ALL_SET:
MOV DX,CS:[FLAGBITS] ; GET BITS TO SET IN FLAG FIELD
XOR BH,BH
;
; IN THE VIRTUAL DRIVE SYSTEM WE *MUST* FLAG THE OTHER DRIVES AS BEING CHANGED
;
; ASSUME FIRST BDS IS IN THIS SEGMENT
PUSH AX
PUSH DS ; SAVE CURRENT BDS
PUSH DI
LDS DI,DWORD PTR CS:[START_BDS]
SCAN_BDS:
CMP DI,-1
JZ SKIPSET
CMP BYTE PTR [DI].DRIVENUM,BL
JNZ GET_NEXT_BDS
;
; SOMEONE MAY COMPLAIN, BUT THIS *ALWAYS* MUST BE DONE WHEN A DISK CHANGE IS
; NOTED. THERE ARE *NO* OTHER COMPROMISING CIRCUMSTANCES.
;
SETCHANGED:
OR WORD PTR DS:[DI].FLAGS,DX ; SIGNAL CHANGE ON OTHER DRIVE
GET_NEXT_BDS:
MOV AX,WORD PTR [DI].LINK+2 ; GO TO NEXT BDS
MOV DI,WORD PTR [DI].LINK
MOV DS,AX
JMP SHORT SCAN_BDS
SKIPSET:
POP DI ; RESTORE CURRENT BDS
POP DS
POP AX
POP DX
POP BX
RET
;
; CHECKROMCHANGE - SEE IF EXTERNAL PROGRAM HAS DIDDLED ROM CHANGE LINE.
;
; INPUTS: DS:DI POINTS TO CURRENT BDS.
; OUTPUTS: ZERO SET - NO CHANGE
; ZERO RESET - CHANGE
; REGISTERS MODIFIED: NONE
CHECKROMCHANGE:
MESSAGE FTEST13,<"CHECKROM ">
MNUM FTEST13
MESSAGE FTEST13,<CR,LF>
TEST WORD PTR [DI].FLAGS,FCHANGED
RET
;
; RESETCHANGED - RESTORE VALUE OF CHANGE LINE
;
; INPUTS: DS:DI POINTS TO CURRENT BDS
; OUTPUTS: NONE
; REGISTERS MODIFIED: NONE
public ResetChanged
RESETCHANGED:
MESSAGE FTEST13,<"RESETCHANGED ">
MNUM FTEST13
MESSAGE FTEST13,<CR,LF>
AND WORD PTR DS:[DI].FLAGS,NOT FCHANGED
RET
;
; HASCHANGE - SEE IF DRIVE CAN SUPPLY CHANGE LINE
;
; INPUTS: DS:DI POINTS TO CURRENT BDS
; OUTPUTS: ZERO SET - NO CHANGE LINE AVAILABLE
; ZERO RESET - CHANGE LINE AVAILABLE
; REGISTERS MODIFIED: NONE
PUBLIC HASCHANGE
HASCHANGE:
MESSAGE FTEST13,<"HASCHANGE ">
MNUM FTEST13
MESSAGE FTEST13,<CR,LF>
TEST WORD PTR [DI].FLAGS,FCHANGELINE
RET
ASSUME DS:CODE
INCLUDE MSVOLID.INC
PUBLIC END96TPI
END96TPI LABEL BYTE

281
v4.0/src/BIOS/MSAUX.ASM Normal file
View File

@ -0,0 +1,281 @@
TITLE MSAUX - DOS 3.3
;----------------------------------------------------------------
; :
; A U X - AUXILARY DEVICE DRIVER :
; :
; :
; This file contains the Auxilary Device Driver. The :
; auxilary driver handles calls to and from the RS-232 port. :
; Three devices uses this code: AUX, COM1, and COM2. AUX and :
; COM1 talk to the zero RS-232 card and COM2 talks to the :
; 'one' RS-232 card. The beginning of the interrupt entry :
; point for these devices sets the variable AUXNUM in the :
; msbio.asm module. If the value is 0 the routines in this :
; file will talk to the the 'zero' card. If the value in :
; AUXNUM is 1 the routines will talk to the 'one' card. :
; The procedure GETDX is called to put the value 0 or 1 in :
; the DX register depending on the value in AUXBUF. :
; :
; The routines in this files are: :
; :
; routine function :
; ------- -------- :
; AUX$READ Read characters from the :
; specified device. :
; AUX$RDND Non-desrucrtive read with :
; no waiting. :
; AUX$FLSH Flush specified device input :
; buffer. :
; AUX$WRIT Write characters to the :
; specified device. :
; AUX$WRST Get status of specified :
; device :
; :
; These routines are not called directly. Call are made via :
; the strategy and interrupt entry point (see Device Header). :
; :
; Data structure: :
; The Aux Device has a two byte buffer called AUXBUF. The :
; first byte is for the zero card, the second byte is for the :
; one card. A zero value in the byte indicates the buffer is :
; empty. The routines use GETBX to get the address of the :
; buffer. :
; :
;----------------------------------------------------------------
;;Ver 3.30 modification ---------------------------
itest=0
INCLUDE MSGROUP.INC ;DEFINE CODE SEGMENT
INCLUDE JUMPMAC.INC
INCLUDE MSMACRO.INC
EXTRN ERR$CNT:NEAR ;MSBIO1
EXTRN GETDX:NEAR ;MSBIO1
EXTRN RDEXIT:NEAR ;MSCON
EXTRN EXIT:NEAR ;MSBIO1
EXTRN BUS$EXIT:NEAR ;MSBIO1
;DATA
EXTRN AUXBUF:BYTE ;MSDATA
; VALUES IN AH, REQUESTING FUNCTION OF INT 14H IN ROM BIOS
AUXFUNC_SEND EQU 1 ;TRANSMIT
AUXFUNC_RECEIVE EQU 2 ;READ
AUXFUNC_STATUS EQU 3 ;REQUEST STATUS
; ERROR FLAGS, REPORTED BY INT 14H
; THESE FLAGS REPORTED IN AH:
FLAG_DATA_READY EQU 01H ;DATA READY
FLAG_OVERRUN EQU 02H ;OVERRUN ERROR
FLAG_PARITY EQU 04H ;PARITY ERROR
FLAG_FRAME EQU 08H ;FRAMING ERROR
FLAG_BREAK EQU 10H ;BREAK DETECT
FLAG_TRANHOL_EMP EQU 20H ;TRANSMIT HOLDING REGISTER EMPTY
FLAG_TRANSHF_EMP EQU 40H ;TRANSMIT SHIFT REGISTER EMPTY
FLAG_TIMEOUT EQU 80H ;TIMEOUT
; THESE FLAGS REPORTED IN AL:
FLAG_DELTA_CTS EQU 01H ;DELTA CLEAR TO SEND
FLAG_DELTA_DSR EQU 02H ;DELTA DATA SET READY
FLAG_TRAIL_RING EQU 04H ;TRAILING EDGE RING INDICATOR
FLAG_DELTA_SIG EQU 08H ;DELTA RECEIVE LINE SIGNAL DETECT
FLAG_CTS EQU 10H ;CLEAR TO SEND
FLAG_DSR EQU 20H ;DATA SET READY
FLAG_RING EQU 40H ;RING INDICATOR
FLAG_REC_SIG EQU 80H ;RECEIVE LINE SIGNAL DETECT
;;End of modification ------------------
;----------------------------------------------------------------
; :
; Read zero or more characters from Auxilary Device :
; :
; input:es:[di] points to area to receive aux data :
; cx has number of bytes to be read :
; "auxnum" first byte has number of aux device (rel 0):
; :
;----------------------------------------------------------------
PUBLIC AUX$READ
AUX$READ PROC NEAR
ASSUME DS:CODE ; SET BY AUX DEVICE DRIVER ENTRY ROUTINE
jcxz EXVEC2 ; if no characters, get out
call GETBX ; put address of AUXBUF in BX
xor AX,AX ; clear AX register
xchg AL,[BX] ; Get character , if any, from
; buffer and clear buffer
or AL,AL ; if AL is nonzero there was a
; character in the buffer
jnz AUX2 ; if so skip AUXIN call
AUX1: ;
call AUXIN ; get character from port
AUX2: ;
stosb ; store character
loop AUX1 ; if more character, go around again
EXVEC2: ;
Jump EXIT ; all done, successful exit
AUX$READ ENDP
;
; AUXIN: make a call on ROM BIOS to read character from
; the auxilary device, then do some error checking.
; If an error occurs then AUXIN jumps to ERR$CNT and
; does NOT return to where it was called from.
;
AUXIN PROC NEAR
mov ah,AUXFUNC_RECEIVE
call AUXOP
;check for Frame, Parity, or Overrun errors
;WARNING: these error bits are unpredictable
; if timeout (bit 7) is set
test ah,FLAG_FRAME or FLAG_PARITY or FLAG_OVERRUN
jz AROK ;No error if all bits are clear
;Error getting character
add sp,+2 ;Remove rtn address (near call)
xor al,al
or al,FLAG_REC_SIG or FLAG_DSR or FLAG_CTS
JUMP ERR$CNT
AROK:
RET ;CHAR JUST READ IS IN AL, STATUS IS IN AH
AUXIN ENDP
;----------------------------------------------------------------
; :
; Aux non-destructive read with no waiting :
; :
; input: es:[di] points to area to receive aux data :
; :
;----------------------------------------------------------------
;
PUBLIC AUX$RDND
AUX$RDND PROC NEAR
ASSUME DS:CODE ; SET BY AUX DEVICE DRIVER ENTRY ROUTINE
call GETBX ; have BX point to AUXBUF
mov AL,[BX] ; copy contents of buffer to AL
or AL,AL ; if AL is non-zero (char in buffer)
jnz AUXRDX ; then return character
call AUXSTAT ; if not, get status of AUX device
TEST AH,FLAG_DATA_READY ;TEST DATA READY
jz AUXBUS ; then device is busy (not ready)
TEST AL,FLAG_DSR ;TEST DATA SET READY
jz AUXBUS ; then device is busy (not ready)
call AUXIN ; else aux is ready, get character
call GETBX ; have bx point to AUXBUF
mov [BX],AL ; save character in buffer
AUXRDX: ;
Jump RDEXIT ; return character
AUXBUS: ;
Jump BUS$EXIT ; jump to device busy exit
AUX$RDND ENDP
;----------------------------------------------------------------
; :
; Aux Output Status :
; :
;----------------------------------------------------------------
PUBLIC AUX$WRST
AUX$WRST PROC NEAR
ASSUME DS:CODE ; SET BY AUX DEVICE DRIVER ENTRY ROUTINE
call AUXSTAT ; get status of AUX in AX
; now test to see if device is busy
; if this bit is not set,
;;Ver 3.30 modification -----------------------
TEST AL,FLAG_DSR ;TEST DATA SET READY
jz AUXBUS ; then device is busy (not ready)
TEST AH,FLAG_TRANHOL_EMP ;TEST TRANSMIT HOLD REG EMPTY
;;End of modification -------------------------
jz AUXBUS ; then device is busy (not ready)
Jump Exit
AUX$WRST ENDP
;
; AUXSTAT makes a call on the ROM-BIOS to determine the status
; of the auxilary device
; Outputs:
; AX is filled with status of port.
; DX is changes to specify which card - either 0, 1 (, 2, 3) ;ba
; NO other registers are modified
;
AUXSTAT proc near
mov ah,AUXFUNC_STATUS
call AUXOP
ret
AUXSTAT endp
AUXOP PROC NEAR
;AH=FUNCTION CODE
;0=INIT, 1=SEND, 2=RECEIVE, 3=STATUS
call GETDX ; have DX point to proper card
int 14h ; call rom-bios for status
ret
AUXOP ENDP
;----------------------------------------------------------------
; :
; Flush AUX Input buffer - set contents of AUXBUF to zero :
; :
;----------------------------------------------------------------
PUBLIC AUX$FLSH
AUX$FLSH PROC NEAR
ASSUME DS:CODE ; SET BY AUX DEVICE DRIVER ENTRY ROUTINE
call GETBX ; get BX to point to AUXBUF
mov BYTE PTR [BX],0 ; zero out buffer
Jump Exit ; all done, successful return
AUX$FLSH ENDP
;----------------------------------------------------------------
; :
; Write to Auxilary Device :
; :
;----------------------------------------------------------------
PUBLIC AUX$WRIT
AUX$WRIT PROC NEAR
ASSUME DS:CODE ; SET BY AUX DEVICE DRIVER ENTRY ROUTINE
jcxz EXVEC2 ; if CX is zero, no characters
; to be written, jump to exit
AUX$LOOP:
mov AL,ES:[DI] ; get character to be written
inc DI ; move DI pointer to next character
;;Ver 3.30 modification ---------------------------
MOV AH,AUXFUNC_SEND ;VALUE=1, INDICATES A WRITE
CALL AUXOP ;SEND CHARACTER OVER AUX PORT
TEST AH,FLAG_TIMEOUT ;CHECK FOR ERROR
;;End of modification ---------------------------
jz AWOK ; then no error
mov AL,10 ; else indicate write fault
Jump ERR$CNT ; call error routines
; if CX is non-zero, still more
AWOK:
loop AUX$LOOP ; more characrter to print
Jump Exit ; all done, successful return
AUX$WRIT ENDP
;
; GETBX puts the address of AUXBUF (the Auxilary Device buffer)
; in BX. After calling GETBX, a routine can get to AUXBUF
; with [BX].
;
; NOTE: The getdx routine is in msbio1 and looks like:
; mov dx,word ptr cs:[auxnum]
;
GETBX PROC NEAR
call GETDX
mov BX,DX
add BX,OFFSET AUXBUF
ret
GETBX ENDP
CODE ENDS
END

722
v4.0/src/BIOS/MSBDATA.INC Normal file
View File

@ -0,0 +1,722 @@
;==============================================================================
;REVISION HISTORY:
;AN000 - New for DOS Version 3.4 - J.K.
;AC000 - Changed for DOS Version 3.4 - J.K.
;ANxxx - PTR, DCRs
;==============================================================================
;AN001 - d9 Double word MOV instruction for 80386 based machine. 7/1/87 J.K.
;AN002 - d25 Change DASD ERP to that recommended by Storage Systems. 7/29/87 J.K.
;AN003; d304 Boot record structure change for OS2 11/9/87 J.K.
;==============================================================================
EXTRN INIT:NEAR
PUBLIC START$
START$:
JMP INIT ;START$ PATCH BY INIT TO POINT TO
;HDRIVE BPB
; PUBLIC FORMAT_PATCH
;FORMAT_PATCH: ;ARR 2.42
; JMP FMTSET ;MJB001 DISPATCH FOR CALL FROM FORMAT UTILITY
PATHSTART 001,BIO
; DB 20 DUP (0) ;IBM WANTS SOME ZEROED AREA (DELETED)
;HEADER DB "Ver 2.45"
;--------------------------------------------------------------
;
; COMMAND JUMP TABLES
;
; BEWARE - THESE TABLES OVERLAP SOMEWHAT! -C.P.
;
ODD
DSKTBL LABEL BYTE
DB 24 ; THIS IS THE SIZE OF THE TABLE YUK!!!!
DW DSK$INIT
DW MEDIA$CHK
DW GET$BPB
DW CMDERR ;RS
DW DSK$READ
DW BUS$EXIT
DW EXIT
DW EXIT
DW DSK$WRIT
DW DSK$WRITV
DW EXIT ;ARR 2.41
DW EXIT ;ARR 2.41
DW CMDERR ;RS
PUBLIC TABLE_PATCH
TABLE_PATCH LABEL WORD ;ARR 2.42
DW DSK$OPEN ;ARR 2.41
DW DSK$CLOSE ;ARR 2.41
DW DSK$REM ;ARR 2.41
DW EXIT
DW EXIT
DW EXIT
DW GENERIC$IOCTL ; KGS 3.20
DW EXIT
DW EXIT
DW EXIT
DW IOCTL$GETOWN ; RS 3.20
DW IOCTL$SETOWN ; RE 3.20
ODD
CONTBL LABEL BYTE
DB 10
DW EXIT
DW EXIT
DW EXIT
DW CMDERR
DW CON$READ
DW CON$RDND
DW EXIT
DW CON$FLSH
DW CON$WRIT
DW CON$WRIT
DW EXIT ;ARR 2.41
; DW CMDERR ;J.K. 4/29/86 for CON$GENIOCTL support
; DW CMDERR ;J.K. 4/29/86
; DW CMDERR ;J.K. 4/29/86
; DW CMDERR ;J.K. 4/29/86
; DW CMDERR ;J.K. 4/29/86
; DW CMDERR ;J.K. 4/29/86
; DW CMDERR ;J.K. 4/29/86
; DW CMDERR ;J.K. 4/29/86
; DW CON$GENIOCTL ;J.K. 4/29/86
ODD
AUXTBL LABEL BYTE
DB 10
DW EXIT
DW EXIT
DW EXIT
DW CMDERR
DW AUX$READ
DW AUX$RDND
DW EXIT
DW AUX$FLSH
DW AUX$WRIT
DW AUX$WRIT
DW AUX$WRST
ODD
TIMTBL LABEL BYTE
DB 9
DW EXIT
DW EXIT
DW EXIT
DW CMDERR
DW TIM$READ
DW BUS$EXIT
DW EXIT
DW EXIT
DW TIM$WRIT
DW TIM$WRIT
ODD
PRNTBL LABEL BYTE
DB 24
DW EXIT ;INIT
DW EXIT
DW EXIT
DW CMDERR
DW EXIT$ZER ;INDICATE ZERO CHARS READ
DW BUS$EXIT
DW EXIT
DW EXIT
DW PRN$WRIT
DW PRN$WRIT
DW PRN$STAT
DW EXIT
DW EXIT ;ARR 2.41
DW EXIT ;ARR 2.41
DW EXIT ;ARR 2.41
DW EXIT ;ARR 2.41
DW PRN$TILBUSY
DW EXIT ;RS 3.20
DW EXIT ;RS 3.20
DW PRN$GENIOCTL ;RS 3.20
DW EXIT ;RS 3.20
DW EXIT ;RS 3.20
DW EXIT ;RS 3.20
DW CMDERR ;RS 3.20
DW CMDERR ;RS 3.20
EVENB
PUBLIC OLD13 ;(MOVED HERE FROM IBMBIO2)
OLD13 label DWORD
db '5986' ;J.K. 11/7/86 Secrete Code for DOS 3.30 IBMBIO.
PUBLIC ORIG13
ORIG13 label DWORD
db '21',0,0 ;J.K. 11/8/86 This is my employee serial # !!!
EVENB
PUBLIC PTRSAV
PTRSAV DD 0
PUBLIC AUXBUF
AUXBUF DB 0,0,0,0 ;SET OF 1 BYTE BUFFERS FOR COM 1,2,3, AND 4
EVENB
PUBLIC PREVOPER,NUMBER_OF_SEC
PREVOPER DW ? ; HOLDS INT 13 REQUEST (I.E. REGISTER AX).
NUMBER_OF_SEC DB ? ; HOLDS NUMBER OF SECTORS TO READ ON AN ECC ERROR
IF ($-CODE) GT 100H
%OUT VDISK BUFFER NOT CORRECTLY LOCATED
ELSE
ORG 100H
ENDIF
PUBLIC VDISK_AREA
VDISK_AREA DB 108 DUP(0) ;FOR USE BY VDISK
EVENB
; WARNING!!! THESE ARE ADDRESSED TOGETHER IN GETDX
AUXNUM DB 0 ;WHICH AUX DEVICE WAS REQUESTED
DB 0
EVENB
PUBLIC CONHEADER
CONHEADER LABEL WORD ;HEADER FOR DEVICE "CON"
DD AUXDEV2
DW 1000000000010011B ;CON IN AND CON OUT + SPECIAL
DW STRATEGY
DW CON$IN
DB 'CON '
EVENB
PUBLIC AUXDEV2
AUXDEV2 LABEL WORD ;HEADER FOR DEVICE "AUX"
DD PRNDEV2
DW 1000000000000000B
DW STRATEGY
DW AUX0$IN
DB 'AUX '
EVENB
PUBLIC PRNDEV2
PRNDEV2 LABEL WORD ;HEADER FOR DEVICE "PRN"
DD TIMDEV
DW CHARDEV + OUTTILBUSY + DEV320
DW STRATEGY
DW PRN0$IN
DB 'PRN '
EVENB
PUBLIC TIMDEV
TIMDEV LABEL WORD
DD DSKDEV
DW 1000000000001000B
DW STRATEGY
DW TIM$IN
DB 'CLOCK$ '
EVENB
PUBLIC DSKDEV
DSKDEV LABEL WORD
DD COM1DEV
DW 0000100001000010B ;J.K.I1. 32 bit sector calculation
DW STRATEGY
DW DSK$IN
DRVMAX DB 4
PUBLIC DRVMAX
PUBLIC STEP_DRV
STEP_DRV DB -2 ; ARR 2.20 LAST DRIVE ACCESSED
PUBLIC PHYS_DRV
PHYS_DRV DB 0 ; USED BY SETDRIVE FOR GETTING BDS FOR
; LOGICAL DRIVE, OR PHYSICAL DRIVE.
PUBLIC FHAVE96
FHAVE96 DB 0 ; FLAG TO INDICATE PRESENCE OF
; 96TPI SUPPORT
PUBLIC SINGLE
SINGLE DB 0 ; USED TO DETECT SINGLE DRIVE SYSTEMS
PUBLIC FHAVEK09
FHAVEK09 DB 0 ;INDICATES IF THIS IS A K09 OR NOT
; USED BY CONSOLE DRIVER.
PUBLIC NEW_ROM
NEW_ROM DB 0 ;SET TO 1 IF WE HAVE A ROM THAT CAN
; HANDLE STRANGE MEDIA LAYOUTS.
PUBLIC FSETOWNER
FSETOWNER DB ? ;=1 IF WE ARE SETTING THE OWNER OF A
;DRIVE. (EXAMINED BY CHECKSINGLE).
public Secrete_Code
Secrete_Code dw 'jk' ;J.K. 11/7/86 Secrete code for DOS 3.30 IBMBIO.
EVENB
PUBLIC COM1DEV
COM1DEV LABEL WORD
DD LPT1DEV
DW 1000000000000000B
DW STRATEGY
DW AUX0$IN
DB 'COM1 '
EVENB
PUBLIC LPT1DEV
LPT1DEV LABEL WORD
DD LPT2DEV
DW CHARDEV + OUTTILBUSY + DEV320
DW STRATEGY
DW PRN1$IN
DB 'LPT1 '
EVENB
PUBLIC LPT2DEV
LPT2DEV LABEL WORD
DD LPT3DEV
DW CHARDEV + OUTTILBUSY + DEV320
DW STRATEGY
DW PRN2$IN
DB 'LPT2 '
EVENB
PUBLIC LPT3DEV
LPT3DEV LABEL WORD
DD COM2DEV
DW CHARDEV + OUTTILBUSY + DEV320
DW STRATEGY
DW PRN3$IN
DB 'LPT3 '
EVENB
PUBLIC COM2DEV
COM2DEV LABEL WORD
DD COM3DEV
DW 1000000000000000B
DW STRATEGY
DW AUX1$IN
DB 'COM2 '
EVENB
PUBLIC COM3DEV
COM3DEV LABEL WORD ;EDK
DD COM4DEV
DW 1000000000000000B
DW STRATEGY
DW AUX2$IN
DB 'COM3 '
EVENB
PUBLIC COM4DEV
COM4DEV LABEL WORD ;EDK
DW -1,CODE
DW 1000000000000000B
DW STRATEGY
DW AUX3$IN
DB 'COM4 '
; HARD-WIRE THE LINK TO THE NEXT INT2F HANDLER.
EVENB
PUBLIC NEXT2F_13
NEXT2F_13 LABEL WORD
EXTRN INT2F_DISK:FAR ;IBMBIO2
DD INT2F_DISK
EVENB
PUBLIC START_BDS
START_BDS LABEL WORD
DD BDS1 ;START OF BDS LINKED LIST.
PUBLIC ACCESSCOUNT
ACCESSCOUNT DB 0 ; NUMBER OF TIMES MEDIA CHECK CALLED
PUBLIC TIM_DRV
TIM_DRV DB -1 ; TIME WHEN LAST DISK I/O PERFORMED
PUBLIC FLAGBITS
FLAGBITS DW 0 ; BITS TO SET IN FLAG FIELD WHEN DOING
; A SET_CHANGED_DL
PUBLIC MEDBYT
MEDBYT DB ?
EVENB
PUBLIC WRTVERIFY
WRTVERIFY LABEL WORD
PUBLIC RFLAG
RFLAG DB ROMREAD ;2 FOR READ, 3 FOR WRITE
VERIFY DB 0 ;1 IF VERIFY AFTER WRITE
PUBLIC SECCNT
SECCNT DW 0
PUBLIC HARDNUM
HARDNUM DB 99 ;LOGICAL DRIVE NUMBER OF FIRST HARDFILE
PUBLIC MOTORSTARTUP,SETTLECURRENT,SETTLESLOW
MOTORSTARTUP DB ? ; VALUE FROM TABLE
SETTLECURRENT DB ? ; VALUE FROM TABLE
SETTLESLOW DB ? ; SLOW SETTLE VALUE
NEXTSPEED DB ? ; VALUE OF SPEED TO BE USED
public save_head_sttl
Save_head_sttl db ? ;used by READ_SECTOR routine
PUBLIC EOT
EOT DB 9
EVENB
PUBLIC DPT
DPT DD ?
;KEEP THE NEXT TWO ITEMS CONTIGUOUS - SEE IOCTL_BLOCK FOR REASON
PUBLIC CURSEC,CURHD,CURTRK,SPSAV
CURSEC DB 0 ;CURRENT SECTOR
CURHD DB 0 ;CURRENT HEAD
CURTRK DW 0 ;CURRENT TRACK
SPSAV DW 0 ;SAVE THE STACK POINTER
; THE FOLLOWING ARE USED FOR IOCTL FUNCTION CALLS
PUBLIC FORMT_EOT,HDNUM,TRKNUM,GAP_PATCH
FORMT_EOT DB 8 ; EOT USED FOR FORMAT
HDNUM DB 0 ; HEAD NUMBER
TRKNUM DW 0 ; TRACK BEING MANIPULATED
GAP_PATCH DB 50H ; FORMAT GAP PATCHED INTO DPT
;DISK ERRORS RETURNED FROM THE IBM ROM
PUBLIC ERRIN
ERRIN LABEL BYTE
db 0cch ;AN002; Write Fault error
DB 80H ;NO RESPONSE
DB 40H ;SEEK FAILURE
DB 10H ;BAD CRC
DB 8 ;DMA OVERRUN
DB 6 ; MEDIA CHANGE
DB 4 ;SECTOR NOT FOUND
DB 3 ;WRITE ATTEMPT TO WRITE-PROTECT DISK
PUBLIC LSTERR
LSTERR DB 0 ;ALL OTHER ERRORS
;RETURNED ERROR CODES CORRESPONDING TO ABOVE
PUBLIC ERROUT
ERROUT LABEL BYTE
db 10 ;AN002; Write Fault error
DB 2 ;NO RESPONSE
DB 6 ;SEEK FAILURE
DB 4 ;BAD CRC
DB 4 ;DMA OVERRUN
DB 15 ; INVALID MEDIA CHANGE
DB 8 ;SECTOR NOT FOUND
DB 0 ;WRITE ATTEMPT ON WRITE-PROTECT DISK
DB 12 ;GENERAL ERROR
PUBLIC NUMERR
NUMERR = ERROUT-ERRIN
;-------------------------------------------------------------
; READ IN BOOT SECTOR HERE, READ DONE IN READBOOT.
; ALSO READ SECTOR FOR DMA CHECK FOR HARD DISK.
;J.K. The buffer for a disk sector is going to be at a double word boundary
; for 80386 machine.
IF ($-CODE) Mod 4 ;AN001;
Org ($-CODE)+4-(($-CODE) Mod 4) ;AN001;
ENDIF ;AN001;
PUBLIC DISKSECTOR
DiskSector DB 11 DUP(?) ; TAKE CARE OF 3 JUMP BYTES PLUS OEM NAME.
PUBLIC BPB_IN_SECTOR
Bpb_In_Sector DW ?
PUBLIC SECPERCLUSINSECTOR
SecPerClusInSector DB ?
DW ?
public NumberOfFats
NumberOfFats DB ?
DW ?
DW ?
PUBLIC MEDIABYTE
MediaByte DB ?
DW ?
DW ?
DW ?
DW ?
DW ? ;AN000; Extended Hidden sector (high)
DW ? ;AN000; Extended Total sector (low)
DW ? ;AN000; Extended Total sector (high)
db ? ;AN003; PHYDRV in boot record.
db ? ;AN003; CURRENT HEAD in boot record.
public Ext_Boot_Sig
Ext_Boot_Sig DB ? ;AN000; Extended Boot record sig. (=90h)
public Boot_Serial_L
Boot_Serial_L DW ? ;AN000; Boot volume serial number (Low)
public Boot_Serial_H
Boot_Serial_H DW ? ;AN000; Boot volume serial number (High)
public Boot_Volume_Label
Boot_Volume_Label DB 11 dup (' ') ;AN000; Volume label
public Boot_System_ID
Boot_System_ID DB 8 dup (' ') ;AN000; File system Id.
DB 512-($-DISKSECTOR) DUP (?)
;*********************************************************************
; "BDS" CONTAINS INFORMATION FOR EACH DRIVE IN THE SYSTEM.
; VARIOUS VALUES ARE PATCHED WHENEVER ACTIONS ARE PERFORMED.
; SECTORS/ALLOC. UNIT IN BPB INITIALLY SET TO -1 TO SIGNIFY THAT
; THE BPB HAS NOT BEEN FILLED. LINK ALSO SET TO -1 TO SIGNIFY END
; OF LIST. # OF CYLINDERS IN MAXPARMS INITIALIZED TO -1 TO INDICATE
; THAT THE PARAMETERS HAVE NOT BEEN SET.
;
EVENB
BDS1 LABEL WORD
DD BDS2 ;LINK TO NEXT STRUCTURE
DB 0 ;INT 13 DRIVE NUMBER
DB 0 ;LOGICAL DRIVE LETTER
PUBLIC FDRIVE1
FDRIVE1 DW 512 ;PHYSICAL SECTOR SIZE IN BYTES
DB -1 ;SECTORS/ALLOCATION UNIT
DW 1 ;RESERVED SECTORS FOR DOS
DB 2 ;NO. ALLOCATION TABLES
DW 64 ;NUMBER DIRECTORY ENTRIES
DW 9*40 ;NUMBER SECTORS (AT 512 BYTES EA.)
DB 00000000B ;MEDIA DESCRIPTOR, INITIALLY 00H.
DW 2 ;NUMBER OF FAT SECTORS
DW 9 ;SECTOR LIMIT
DW 1 ;HEAD LIMIT
DW 0 ;HIDDEN SECTOR COUNT (low word)
dw 0 ;J.K. Hidden sector (high)
dw 0 ;J.K. Number sectors (low)
dw 0 ;J.K. Number sectors (high)
DB 0 ; TRUE => LARGE FATS
OPCNT1 DW 0 ;OPEN REF. COUNT
DB 3 ;FORM FACTOR
FLAGS1 DW 0020H ;VARIOUS FLAGS
; DB 9 DUP (0) ;RESERVED FOR FUTURE USE
DW 40 ; NUMBER OF CYLINDERS
; RECOMMENDED BPB FOR DRIVE.
RECBPB1 DW 512 ;BYTES PER SECTOR
DB 1 ;SECTORS/ALLOCATION UNIT
DW 1 ;RESERVED SECTORS FOR DOS
DB 2 ;NO. ALLOCATION TABLES
DW 0E0H ;NUMBER DIRECTORY ENTRIES
DW 9*40 ;NUMBER SECTORS (AT 512 BYTES EA.)
DB 0F0H ;MEDIA DESCRIPTOR, INITIALLY F0H.
DW 2 ;NUMBER OF FAT SECTORS
DW 9 ;SECTOR LIMIT
DW 2 ;HEAD LIMIT
DW 0 ;HIDDEN SECTOR COUNT(low)
dw 0 ;J.K. Hidden sector count (high)
dw 0 ;J.K. Number sectors (low)
dw 0 ;J.K. Number sectors (high)
DB 6 DUP (?)
TRACK1 DB -1 ;LAST TRACK ACCESSED ON THIS DRIVE
TIM_LO1 DW -1 ;KEEP THESE TWO CONTIGUOUS (?)
TIM_HI1 DW -1
VOLID1 DB "NO NAME ",0 ;VOLUME ID FOR THIS DISK
VOLSER1 dd 0 ;Current volume serial number from Boot record
SYSID1 db "FAT12 ",0 ;Current file system id from Boot record
EVENB
BDS2 LABEL WORD
DD BDS3 ;LINK TO NEXT STRUCTURE
DB 0 ;INT 13 DRIVE NUMBER
DB 0 ;LOGICAL DRIVE LETTER
PUBLIC FDRIVE2
FDRIVE2 DW 512 ;PHYSICAL SECTOR SIZE IN BYTES
DB -1 ;SECTORS/ALLOCATION UNIT
DW 1 ;RESERVED SECTORS FOR DOS
DB 2 ;NO. ALLOCATION TABLES
DW 64 ;NUMBER DIRECTORY ENTRIES
DW 9*40 ;NUMBER SECTORS (AT 512 BYTES EA.)
DB 00000000B ;MEDIA DESCRIPTOR, INITIALLY 00H.
DW 2 ;NUMBER OF FAT SECTORS
DW 9 ;SECTOR LIMIT
DW 1 ;HEAD LIMIT
DW 0 ;HIDDEN SECTOR COUNT (low word)
dw 0 ;J.K. Hidden sector (high)
dw 0 ;J.K. Number sectors (low)
dw 0 ;J.K. Number sectors (high)
DB 0 ; TRUE => LARGE FATS
OPCNT2 DW 0 ;OPEN REF. COUNT
DB 3 ;FORM FACTOR
FLAGS2 DW 0020H ;VARIOUS FLAGS
; DB 9 DUP (0) ;RESERVED FOR FUTURE USE
DW 40 ; NUMBER OF CYLINDERS
; RECOMMENDED BPB FOR DRIVE.
RECBPB2 DW 512 ;BYTES PER SECTOR
DB 1 ;SECTORS/ALLOCATION UNIT
DW 1 ;RESERVED SECTORS FOR DOS
DB 2 ;NO. ALLOCATION TABLES
DW 0E0H ;NUMBER DIRECTORY ENTRIES
DW 9*40 ;NUMBER SECTORS (AT 512 BYTES EA.)
DB 0F0H ;MEDIA DESCRIPTOR, INITIALLY F0H.
DW 2 ;NUMBER OF FAT SECTORS
DW 9 ;SECTOR LIMIT
DW 2 ;HEAD LIMIT
DW 0 ;HIDDEN SECTOR COUNT(low)
dw 0 ;J.K. Hidden sector count (high)
dw 0 ;J.K. Number sectors (low)
dw 0 ;J.K. Number sectors (high)
DB 6 DUP (?)
TRACK2 DB -1 ;LAST TRACK ACCESSED ON THIS DRIVE
TIM_LO2 DW -1 ;KEEP THESE TWO CONTIGUOUS (?)
TIM_HI2 DW -1
VOLID2 DB "NO NAME ",0 ;VOLUME ID FOR THIS DISK
VOLSER2 dd 0 ;Current volume serial number from Boot record
SYSID2 db "FAT12 ",0 ;Current file system id from Boot record
EVENB
BDS3 LABEL WORD
DD BDS4 ;LINK TO NEXT STRUCTURE
DB 0 ;INT 13 DRIVE NUMBER
DB 0 ;LOGICAL DRIVE LETTER
PUBLIC FDRIVE3
FDRIVE3 DW 512 ;PHYSICAL SECTOR SIZE IN BYTES
DB -1 ;SECTORS/ALLOCATION UNIT
DW 1 ;RESERVED SECTORS FOR DOS
DB 2 ;NO. ALLOCATION TABLES
DW 64 ;NUMBER DIRECTORY ENTRIES
DW 9*40 ;NUMBER SECTORS (AT 512 BYTES EA.)
DB 00000000B ;MEDIA DESCRIPTOR, INITIALLY 00H.
DW 2 ;NUMBER OF FAT SECTORS
DW 9 ;SECTOR LIMIT
DW 1 ;HEAD LIMIT
DW 0 ;HIDDEN SECTOR COUNT (low word)
dw 0 ;J.K. Hidden sector (high)
dw 0 ;J.K. Number sectors (low)
dw 0 ;J.K. Number sectors (high)
DB 0 ; TRUE => LARGE FATS
OPCNT3 DW 0 ;OPEN REF. COUNT
DB 3 ;FORM FACTOR
FLAGS3 DW 0020H ;VARIOUS FLAGS
; DB 9 DUP (0) ;RESERVED FOR FUTURE USE
DW 40 ; NUMBER OF CYLINDERS
; RECOMMENDED BPB FOR DRIVE.
RECBPB3 DW 512 ;BYTES PER SECTOR
DB 1 ;SECTORS/ALLOCATION UNIT
DW 1 ;RESERVED SECTORS FOR DOS
DB 2 ;NO. ALLOCATION TABLES
DW 0E0H ;NUMBER DIRECTORY ENTRIES
DW 9*40 ;NUMBER SECTORS (AT 512 BYTES EA.)
DB 0F0H ;MEDIA DESCRIPTOR, INITIALLY F0H.
DW 2 ;NUMBER OF FAT SECTORS
DW 9 ;SECTOR LIMIT
DW 2 ;HEAD LIMIT
DW 0 ;HIDDEN SECTOR COUNT(low)
dw 0 ;J.K. Hidden sector count (high)
dw 0 ;J.K. Number sectors (low)
dw 0 ;J.K. Number sectors (high)
DB 6 DUP (?)
TRACK3 DB -1 ;LAST TRACK ACCESSED ON THIS DRIVE
TIM_LO3 DW -1 ;KEEP THESE TWO CONTIGUOUS (?)
TIM_HI3 DW -1
VOLID3 DB "NO NAME ",0 ;VOLUME ID FOR THIS DISK
VOLSER3 dd 0 ;Current volume serial number from Boot record
SYSID3 db "FAT12 ",0 ;Current file system id from Boot record
EVENB
BDS4 LABEL WORD
DW -1 ;LINK TO NEXT STRUCTURE
DW CODE
DB 0 ;INT 13 DRIVE NUMBER
DB 0 ;LOGICAL DRIVE LETTER
PUBLIC FDRIVE4
FDRIVE4 DW 512 ;PHYSICAL SECTOR SIZE IN BYTES
DB -1 ;SECTORS/ALLOCATION UNIT
DW 1 ;RESERVED SECTORS FOR DOS
DB 2 ;NO. ALLOCATION TABLES
DW 64 ;NUMBER DIRECTORY ENTRIES
DW 9*40 ;NUMBER SECTORS (AT 512 BYTES EA.)
DB 00000000B ;MEDIA DESCRIPTOR, INITIALLY 00H.
DW 2 ;NUMBER OF FAT SECTORS
DW 9 ;SECTOR LIMIT
DW 1 ;HEAD LIMIT
DW 0 ;HIDDEN SECTOR COUNT (low word)
dw 0 ;J.K. Hidden sector (high)
dw 0 ;J.K. Number sectors (low)
dw 0 ;J.K. Number sectors (high)
DB 0 ; TRUE => LARGE FATS
OPCNT4 DW 0 ;OPEN REF. COUNT
DB 3 ;FORM FACTOR
FLAGS4 DW 0020H ;VARIOUS FLAGS
; DB 9 DUP (0) ;RESERVED FOR FUTURE USE
DW 40 ; NUMBER OF CYLINDERS
; RECOMMENDED BPB FOR DRIVE.
RECBPB4 DW 512 ;BYTES PER SECTOR
DB 1 ;SECTORS/ALLOCATION UNIT
DW 1 ;RESERVED SECTORS FOR DOS
DB 2 ;NO. ALLOCATION TABLES
DW 0E0H ;NUMBER DIRECTORY ENTRIES
DW 9*40 ;NUMBER SECTORS (AT 512 BYTES EA.)
DB 0F0H ;MEDIA DESCRIPTOR, INITIALLY F0H.
DW 2 ;NUMBER OF FAT SECTORS
DW 9 ;SECTOR LIMIT
DW 2 ;HEAD LIMIT
DW 0 ;HIDDEN SECTOR COUNT(low)
dw 0 ;J.K. Hidden sector count (high)
dw 0 ;J.K. Number sectors (low)
dw 0 ;J.K. Number sectors (high)
DB 6 DUP (?)
TRACK4 DB -1 ;LAST TRACK ACCESSED ON THIS DRIVE
TIM_LO4 DW -1 ;KEEP THESE TWO CONTIGUOUS (?)
TIM_HI4 DW -1
VOLID4 DB "NO NAME ",0 ;VOLUME ID FOR THIS DISK
VOLSER4 dd 0 ;Current volume serial number from Boot record
SYSID4 db "FAT12 ",0 ;Current file system id from Boot record
BPBTYPE STRUC
SPF DB ?
SPT DB ?
CDIRE DB ?
CSEC DW ?
SPA DB ?
CHEAD DB ?
BPBTYPE ENDS
PUBLIC SM92
SM92 BPBTYPE <3,9,70H,2*9*80,2,2>
;-----------------------------------------------
;
; C O N - CONSOLE DEVICE DRIVER
;
PUBLIC ALTAH
ALTAH DB 0 ;SPECIAL KEY HANDLING
public KEYRD_Func
KEYRD_Func DB 0 ;AN000; Default is conventional keyboard read
public KEYSTS_Func
KEYSTS_Func DB 1 ;AN000; Defualt if conventional keyboard status check.
; PUBLIC SAV_SC_INFO ;J.K. 4/29/86 FOR CON$GENIOCTL
; PUBLIC SAV_SC_MODE
; PUBLIC SAV_SC_COLORS
; PUBLIC SAV_SC_WIDTH
; PUBLIC SAV_SC_LENGTH
;SAV_SC_INFO LABEL BYTE
;SAV_SC_MODE DB 0
;SAV_SC_COLORS DW 0
;SAV_SC_WIDTH DW 0
;SAV_SC_LENGTH DW 0 ;J.K. 4/29/86 FOR CON$GENIOCTL
;-------------------------------------------------------------
;
; P R N - PRINTER DEVICE
;
PUBLIC PRINTDEV
PRINTDEV DB 0 ; INDEX INTO ABOVE ARRAY
; THE FOLLOWING VARIABLE CAN BE MODIFIED VIA IOCTL SUB-FUNCTION 16. IN THIS
; WAY, THE WAIT CAN BE SET TO SUIT THE SPEED OF THE PARTICULAR PRINTER BEING
; USED. ONE FOR EACH PRINTER DEVICE.
EVENB
PUBLIC WAIT_COUNT
WAIT_COUNT DW 4 DUP (50H) ; ARRAY OF RETRY COUNTS FOR PRINTER
EVENB
PUBLIC DAYCNT
DAYCNT DW 0
IF iTEST ;Testing Mode for IBMBIO.
PUBLIC NUMBUF
NUMBUF DB 5 DUP (?)
PUBLIC DIGITS
DIGITS DB "0123456789ABCDEF"
PUBLIC FTESTBITS
;FTESTBITS DW FTESTDISK+FTESTINIT
FTESTBITS DW fTestDISK
;ftestbits dw ftestclock
ENDIF
PATHEND 001,BIO


14
v4.0/src/BIOS/MSBIO.LNK Normal file
View File

@ -0,0 +1,14 @@
msbio1+
msCON+
msAUX+
msLPT+
msCLOCK+
msDISK+
msBIO2+
mshard+
msinit+
sysinit1+
sysconf+
sysinit2+
sysimes,msbio,msBIO/M;


139
v4.0/src/BIOS/MSBIO.SKL Normal file
View File

@ -0,0 +1,139 @@
;==============================================================================
;REVISION HISTORY:
;AN000 - New for DOS Version 4.0 - J.K.
;AC000 - Changed for DOS Version 4.0 - J.K.
;AN00x - PTM number for DOS Version 4.0 - J.K.
;==============================================================================
;==============================================================================
;AN001 D246, P976 Show "Bad command or parameters - ..." msg 9/22/87 J.K.
;AN002 D274 Take "file" out from "Incorrect order..." msg 10/07/87 J.K.
;AN003 D486 Share installation for large media 02/24/88 J.K.
;==============================================================================
;===================
:class 1
;===================
; MESSAGES FOR THE IBM BOOT SECTOR. NUL Terminated.
; This is used by IBMBOOT and IBMLOAD program and it stays in IBMBOOT directory.
;For IBMLOAD program
;SYSMSG DB 13,10,"Non-System disk or disk error",13,10
; DB "Replace and strike any key when ready",13,10,0
:use 001 BOOT SYSMSG
;===================
:class 2
;===================
; SCCSID = @(#)biomes.asm 1.2 85/07/25
; SINGLE DRIVE MESSAGE FOR IBMBIO.COM. NUL TERMINATED.
;IFNDEF PATHSTART
;PATHSTART MACRO INDEX,ABBR
; IFDEF PATHGEN
; PUBLIC ABBR&INDEX&S,ABBR&INDEX&E
; ABBR&INDEX&S LABEL BYTE
; ENDIF
; ENDM
;ENDIF
;
;IFNDEF PATHEND
;PATHEND MACRO INDEX,ABBR
; IFDEF PATHGEN
; ABBR&INDEX&E LABEL BYTE
; ENDIF
; ENDM
;ENDIF
; PATHSTART 001,BIOMS
:def 20 SNGMSG DB 13,10,"Insert diskette for drive "
:def 21 DRVLET DB "A: and strike",13,10,"any key when ready",13,10,10,0
; PATHEND 001,BIOMS
;==================
:class 3
;==================
; PRINTED when there is a bad command in CONFIG.SYS. '$' TERMINATED, note
; that this message includes crlfm!
;PATHSTART 001,SYSMES
:def 03 BADOPM DB 13,10,"Unrecognized command in CONFIG.SYS"
;BADSIZ_POST LABEL BYTE
;BADLD_POST LABEL BYTE
:def 04 CRLFM DB 13,10,'$'
:def 22 BadParm db 13,10,"Bad command or parameters - $" ;AN001;
;PRINTED when installed device specifies too large a sector size.'$' terminated.
; FORM: <BADSIZ_PRE>device name<BADSIZ_POST>
:def 05 BADSIZ_PRE DB 13,10,"Sector size too large in file $"
;PRINTED when installed device cannot be found. '$' terminated.
; FORM: <BADLD_PRE>device name<BADLD_POST>
:def 06 BADLD_PRE DB 13,10,"Bad or missing $"
;PRINTED when command interpreter is not found. NUL terminated.
; FORM: <BADLD_PRE><BADCOM><BADLD_POST>
:def 07 BADCOM DB "Command Interpreter",0
;PRINTED when country code, code page combination was not found in country.sys file. '$' terminated.
; FORM: <BADCOUNTRY>
:def 08 BADCOUNTRY DB 13,10,"Invalid country code or code page",13,10,"$"
;PRINTED when code page id is missing or wrong syntax. - J.K.
; FORM: <BADCOUNTRYCOM>
:def 09 BADCOUNTRYCOM DB 13,10,"Error in COUNTRY command",13,10,"$"
;PRINTED when the memory left is not sufficient to handle COUTRY.SYS file
; FORM: <INSUFMEMORY>
:def 10 INSUFMEMORY DB 13,10, "Insufficient memory for COUNTRY.SYS file",13,10,"$"
; PRINTED when there is insufficient memory. '$' TERMINATED, note
; that this message includes crlfm!
:def 11 BADMEM DB 13,10,"Configuration too large for memory",13,10,"$"
; PRINTED when the attempt is made to install a block device which would
; have a drive letter > 'Z'
:def 12 BADBLOCK DB 13,10,"Too many Block Devices",13,10,"$"
; PRINTED when the attempt is made to install a stack with invalid
; combinations of # of stacks, stack size. - J.K. 5/23/86
:def 13 BADSTACK DB 13,10,"Invalid STACK parameters",13,10,"$"
;AN000; - PRINTED when encountering a command that is not "install=" after
; we had a "Install=" command. - J.K.I1.
; Translation::: Please leave the last blank space at the end of the line
; as it is.
:def 14 BADORDER DB 13,10,"Incorrect order in CONFIG.SYS line ","$"
;AN000; - PRINTED when the command failed.
; Translation::: Please leave the last blank space at the end of the line
; as it is.
:def 15 ERRORCMD DB "Error in CONFIG.SYS line ","$"
;AN003; - PRINTED when SHARE.EXE is not loaded and has a large media > 32 MB.
:def 23 SHAREWARNMSG db "WARNING! SHARE should be loaded for large media",13,10,"$"
;==================
:class 4
;==================
;IBMBIO SYSINIT
;Message for SYSINIT_BASE program.
:def 16 Mem_alloc_err db 13,10,"Memory allocation error","$"
;==================
:class 5
;==================
; %OUT STKMES.INC...
; SCCSID = @(#)stkmes.inc 1.0 86/10/21
; PUBLIC FATAL_MSG
:def 17 FATAL_MSG DB 0DH,0AH,7,0DH,0AH
DB "Internal stack overflow",0DH,0AH
DB "System halted",0DH,0AH,"$"
;
:END

645
v4.0/src/BIOS/MSBIO1.ASM Normal file
View File

@ -0,0 +1,645 @@
PAGE ,132 ;
TITLE MSBIO1.asm - BIOS
;==============================================================================
;REVISION HISTORY:
;AN000 - New for DOS Version 4.00 - J.K.
;AC000 - Changed for DOS Version 4.00 - J.K.
;AN00x - PTM number for DOS Version 4.00 - J.K.
;==============================================================================
COMMENT *
THE LINK STEP IS PERFORMED BY USING THE FOLLOWING "NEW.ARF" FILE:
msbio1+
msSTACK+
MsCON+
msAUX+
msLPT+
msCLOCK+
msdISK+
msBIO2+
C:\BIO2\OLDOBJ\disk+
C:\BIO2\OLDOBJ\msinit+
C:\BIO2\OLDOBJ\sysinit1+
C:\BIO2\OLDOBJ\sysinit2+
C:\BIO2\OLDOBJ\sysimes,msbio,/M;
THE FOLLOWING IS A BATCH FILE THAT CAN BE USED TO CREATE THE IBMBIO.COM
WHERE "LOCSCR" IS A FILE THAT JUST HAS THE NUMBER, 70:
link @NEW.ARF
exe2bin ibmbio ibmbio.com <C:\BIO2\Locscr
del ibmbio.exe
(END OF COMMENT)*
;***For testing purposes, set the TEST flag to 1. Otherwise reset it.
iTEST=0
PATHGEN = 1
.SALL
%OUT ...MSBIO1.ASM
; THIS IS A DOSMAC MACRO WHICH IS USED IN DEVSYM WHICH IS INCLUDED LATER
BREAK MACRO SUBTITLE
SUBTTL SUBTITLE
PAGE
ENDM
POPFF MACRO
JMP $+3
IRET
PUSH CS
CALL $-2
ENDM
INCLUDE MSGROUP.INC ;DEFINE CODE SEGMENT
SYSINITSEG SEGMENT PUBLIC 'SYSTEM_INIT'
SYSINITSEG ENDS
INCLUDE JUMPMAC.INC
PATHSTART MACRO INDEX,ABBR
IFDEF PATHGEN
PUBLIC ABBR&INDEX&S,ABBR&INDEX&E
ABBR&INDEX&S LABEL BYTE
ENDIF
ENDM
PATHEND MACRO INDEX,ABBR
IFDEF PATHGEN
ABBR&INDEX&E LABEL BYTE
ENDIF
ENDM
INCLUDE PUSHPOP.INC
INCLUDE DEVSYM.INC ;MJB001
; REV 2.1 5/1/83 ARR ADDED TIMER INT HANDLER AND CHANGED ORDER OF AUX
; PRN INIT FOR HAL0
;
; REV 2.15 7/13/83 ARR BECAUSE IBM IS FUNDAMENTALY BRAIN DAMAGED, AND
; BASCOM IS RUDE ABOUT THE 1CH TIMER INTERRUPT, THE TIMER
; HANDLER HAS TO GO BACK OUT!!!!! IBM SEEMS UNWILLING TO
; BELIEVE THE PROBLEM IS WITH THE BASCOM RUNTIME, NOT THE
; DOS. THEY HAVE EVEN BEEN GIVEN A PATCH FOR BASCOM!!!!!
; THE CORRECT CODE IS COMMENTED OUT AND HAS AN ARR 2.15
; ANNOTATION. THIS MEANS THE BIOS WILL GO BACK TO THE
; MULTIPLE ROLL OVER BUG.
; REV 2.20 8/5/83 ARR IBM MAKES HARDWARE CHANGE. NOW WANTS TO USE HALF
; HIGHT DRIVES FOR HAL0, AND BACK FIT FOR PC/PC XT. PROBLEM
; WITH HEAD SETTLE TIME. PREVIOUS DRIVES GOT BY ON A 0
; SETTLE TIME, 1/2 HIGHT DRIVES NEED 15 HEAD SETTLE WHEN
; DOING WRITES (0 OK ON READ) IF THE HEAD IS BEING STEPPED.
; THIS REQUIRES A LAST TRACK VALUE TO BE KEPT SO THAT BIOS
; KNOWS WHEN HEAD IS BEING MOVED. TO HELP OUT STUPID
; PROGRAMS THAT ISSUE INT 13H DIRECTLY, THE HEAD SETTLE WILL
; NORMALLY BE SET TO 15. IT WILL BE CHANGED TO 0 ON READS,
; OR ON WRITES WHICH DO NOT REQUIRE HEAD STEP.
; REV 2.21 8/11/83 MZ IBM WANTS WRITE WITH VERIFY TO USE HEAD SETTLE 0.
; USE SAME TRICK AS ABOVE.
; REV 2.25 6/20/83 MJB001 ADDED SUPPORT FOR 96TPI AND SALMON
; REV 2.30 6/27/83 MJB002 ADDED REAL-TIME CLOCK
; REV 2.40 7/8/83 MJB003 ADDED VOLUME-ID CHECKING AND INT 2F MACRO
; DEFINITIONS PUSH* AND POP*
; REV 2.41 7/12/83 ARR MORE 2.X ENHANCEMENTS. OPEN/CLOSE MEDIA CHANGE
; REV 2.42 11/3/83 ARR MORE 2.X ENHANCEMENTS. DISK OPEN/CLOSE, FORMAT
; CODE AND OTHER MISC HOOKED OUT TO SHRINK BIOS. CODE FOR
; DISK OPEN/CLOSE, FORMAT INCLUDED ONLY WITH 96TPI DISKS.
; REV 2.43 12/6/83 MZ EXAMINE BOOT SECTORS ON HARD DISKS FOR 16-BIT FAT
; CHECK. EXAMINE LARGE FAT BIT IN BPB FOR WALK OF MEDIA FOR
; DOS
; REV 2.44 12/9/83 ARR CHANGE TO ERROR REPORTING ON INT 17H
; REV 2.45 12/22/83 MZ MAKE HEAD SETTLE CHANGE ONLY WHEN DISK PARM IS 0.
;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
;
; IBM ADDRESSES FOR I/O
;
;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
INCLUDE MSDSKPR.INC
LF = 10 ;LINE FEED
CR = 13 ;CARRIAGE RETURN
BACKSP = 8 ;BACKSPACE
BRKADR = 1BH * 4 ;006C 1BH BREAK VECTOR ADDRESS
TIMADR = 1CH * 4 ;0070 1CH TIMER INTERRUPT
DSKADR = 1EH * 4 ;ADDRESS OF PTR TO DISK PARAMETERS
SEC9 = 522H ;ADDRESS OF DISK PARAMETERS
HEADSETTLE = SEC9+9 ; ARR 2.20 ADDRESS OF HEAD SETTLE TIME
NORMSETTLE = 15 ; ARR 2.20 NORMAL HEAD SETTLE
SPEEDSETTLE = 0 ; ARR 2.20 SPEED UP SETTLE TIME
INITSPOT = 534H ; ARR IBM WANTS 4 ZEROS HERE
AKPORT = 20H
EOI = 20H
ASSUME CS:CODE,DS:NOTHING,ES:NOTHING
EXTRN MEDIA$CHK:NEAR
EXTRN GET$BPB:NEAR
EXTRN DSK$INIT:NEAR
EXTRN DSK$READ:NEAR
EXTRN DSK$WRIT:NEAR
EXTRN DSK$WRITV:NEAR
EXTRN DSK$OPEN:NEAR
EXTRN DSK$CLOSE:NEAR
EXTRN DSK$REM:NEAR
EXTRN GENERIC$IOCTL:NEAR
EXTRN IOCTL$GETOWN:NEAR
EXTRN IOCTL$SETOWN:NEAR
EXTRN CON$READ:NEAR
EXTRN CON$RDND:NEAR
EXTRN CON$FLSH:NEAR
EXTRN CON$WRIT:NEAR
; EXTRN CON$GENIOCTL:NEAR ;J.K. 4/29/86
EXTRN AUX$READ:NEAR
EXTRN AUX$WRIT:NEAR
EXTRN AUX$FLSH:NEAR
EXTRN AUX$RDND:NEAR
EXTRN AUX$WRST:NEAR
EXTRN TIM$READ:NEAR
EXTRN TIM$WRIT:NEAR
EXTRN PRN$WRIT:NEAR
EXTRN PRN$STAT:NEAR
EXTRN PRN$TILBUSY:NEAR
EXTRN PRN$GENIOCTL:NEAR
EXTRN WRMSG:NEAR
;DATA AREAS
extrn Start_Sec_H:word ;AN000; Starting sector high word for
;disk I/O request. IBMDISK.ASM
INCLUDE MSBDATA.INC
IF iTEST
PUBLIC MSGNUM
MSGNUM:
PUSHF
TEST FTESTBITS,AX
JZ MRET
PUSH SI
PUSH BX
PUSH CX
PUSH ES
PUSH DI
MOV DI,OFFSET NUMBUF
PUSH CS
POP ES
MOV CX,4
NUMLOOP:
PUSH CX
MOV CL,4
ROL BX,CL
POP CX
PUSH BX
AND BX,0FH
MOV AL,DIGITS[BX]
STOSB
POP BX
LOOP NUMLOOP
POP DI
POP ES
POP CX
POP BX
MOV SI,OFFSET NUMBUF
CALL MSGOUT
POP SI
POPF
RET
PUBLIC MSGOUT
MSGOUT:
PUSHF
TEST FTESTBITS,AX
JZ MRET
PUSH DS
PUSH AX
PUSH BX
PUSH CS
POP DS
CALL WRMSG
POP BX
POP AX
POP DS
MRET:
POPF
RET
PUBLIC DUMPBYTES ;J.K. 4/9/86
;Dumpbytes will dump the bytes in memory in hex. Space will be put in between
;the bytes and CR, LF will be put at the end. - J.K.
;Input: DS:SI -> buffer to dump in Hex.
; CX -> # of bytes (Length of the buffer)
;
DUMPBYTES proc near
pushf
push ax
dumploops:
lodsb
mov ah, al
shr ah, 1
shr ah, 1
shr ah, 1
shr ah, 1
call hex_to_ascii
push ax
mov al, ah
call outchar
pop ax
call outchar
mov al, ' '
call outchar
loop dumploops
mov al, 0dh
call outchar
mov al, 0ah
call outchar
pop ax
popf
ret
DUMPBYTES endp
PUBLIC Hex_to_ascii
Hex_to_ascii proc near ;J.K. - 4/9/86
and ax, 0f0fh
add ah, 30h
cmp ah, 3ah
jb hta_$1
add ah, 7
hta_$1:
add al, 30h
cmp al, 3ah
jb hta_$2
add al, 7
hta_$2:
ret
Hex_to_ascii endp
PUBLIC outchar
Outchar proc near
PUSH AX
PUSH SI
PUSH DI
PUSH BP
PUSH BX
;SB33002*******************************************************
MOV AH, 0Eh ;SET COMMAND TO WRITE A CHAR ;SB;3.30*
MOV BX, 7 ;SET FOREGROUND COLOR ;SB;3.30*
INT 10h ;CALL ROM-BIOS ;SB;3.30*
;SB33002*******************************************************
POP BX
POP BP
POP DI
POP SI
POP AX
RET
Outchar endp
ENDIF
INCLUDE MSMACRO.INC
;---------------------------------------------------
;
; DEVICE ENTRY POINT
;
CMDLEN = 0 ;LENGTH OF THIS COMMAND
UNIT = 1 ;SUB UNIT SPECIFIER
CMD = 2 ;COMMAND CODE
STATUS = 3 ;STATUS
MEDIA = 13 ;MEDIA DESCRIPTOR
TRANS = 14 ;TRANSFER ADDRESS
COUNT = 18 ;COUNT OF BLOCKS OR CHARACTERS
START = 20 ;FIRST BLOCK TO TRANSFER
EXTRA = 22 ;USUALLY A POINTER TO VOL ID FOR ERROR 15
START_L = 26 ;AN000; Extended start sector (Low)
START_H = 28 ;AN000; Extended start sector (High)
PUBLIC STRATEGY
STRATEGY PROC FAR
MOV WORD PTR CS:[PTRSAV],BX
MOV WORD PTR CS:[PTRSAV+2],ES
RET
STRATEGY ENDP
PUBLIC CON$IN
CON$IN PROC FAR
PUSH SI
MOV SI,OFFSET CONTBL
JMP SHORT ENTRY
CON$IN ENDP
PUBLIC AUX0$IN
AUX0$IN PROC FAR
PUSH SI
PUSH AX
XOR AL,AL
JMP SHORT AUXENT
AUX0$IN ENDP
PUBLIC AUX1$IN
AUX1$IN PROC FAR
PUSH SI
PUSH AX
MOV AL,1
JMP short AUXENT ;J.K. 4/15/86
AUX1$IN ENDP
;SB33102****************************************************************
;SB Add code to handle two more COM Ports
;boban
PUBLIC AUX2$IN
AUX2$IN proc far
push si
push ax
mov al,2
jmp short AUXENT
AUX2$IN endp
PUBLIC AUX3$IN
AUX3$IN proc far
push si
push ax
mov al,3
jmp short AUXENT
;SB33102****************************************************************
AUXENT:
MOV SI,OFFSET AUXTBL
JMP SHORT ENTRY1
AUX3$IN ENDP
PRN0$IN PROC FAR
PUBLIC PRN0$IN
PUSH SI
PUSH AX
XOR AX,AX
JMP SHORT PRNENT
PRN0$IN ENDP
PUBLIC PRN1$IN
PRN1$IN PROC FAR
PUSH SI
PUSH AX
XOR AL,AL
MOV AH,1
JMP SHORT PRNENT
PRN1$IN ENDP
PUBLIC PRN2$IN
PRN2$IN PROC FAR
PUSH SI
PUSH AX
MOV AL,1
MOV AH,2
JMP SHORT PRNENT
PRN2$IN ENDP
PUBLIC PRN3$IN
PRN3$IN PROC FAR
PUSH SI
PUSH AX
MOV AL,2
MOV AH,3
PRNENT:
MOV SI,OFFSET PRNTBL
MOV CS:[PRINTDEV],AH ;SAVE INDEX INTO ARRAY OF RETRY COUNTS
JMP SHORT ENTRY1
PRN3$IN ENDP
PUBLIC TIM$IN
TIM$IN PROC FAR
PUSH SI
MOV SI,OFFSET TIMTBL
JMP SHORT ENTRY
TIM$IN ENDP
PUBLIC DSK$IN
DSK$IN PROC FAR
PUSH SI
MOV SI,OFFSET DSKTBL
ENTRY:
PUSH AX
ENTRY1:
PUSH CX
PUSH DX
PUSH DI
PUSH BP
PUSH DS
PUSH ES
PUSH BX
MOV CS:[AUXNUM],AL ;SAVE CHOICE OF AUX/PRN DEVICE
LDS BX,CS:[PTRSAV] ;GET POINTER TO I/O PACKET
ASSUME DS:NOTHING
MOV AL,BYTE PTR DS:[BX].UNIT ;AL = UNIT CODE
MOV AH,BYTE PTR DS:[BX].MEDIA ;AH = MEDIA DESCRIP
MOV CX,WORD PTR DS:[BX].COUNT ;CX = COUNT
MOV DX,WORD PTR DS:[BX].START ;DX = START SECTOR
;SB34MSB100*********************************************************************
;SB
;SB The disk device driver can now handle 32 bit start sector number.
;SB So we should check to see if a 32 bit sector number has been specified
;SB and if so get it. Whether a 32 bit sector has been specified or not
;SB the disk driver expects a 32 bit sector number with the high word
;SB in cs:Start_Sec_H and the low word in dx.
;SB
;SB Algorithm:
;SB 1. Check to see if the request is for the disk driver by
;SB checking to see if SI points to DSKTBL.
;SB
;SB 2. If request not for the disk nothing special needs to be done.
;SB
;SB 3. If request for the disk then check to see if a 32 bit
;SB sector number has been specified by seeing whether the
;SB the conventional sector number specified is -1. If so
;SB we need to pick the 32 bit sector number from the new
;SB fields in the request packet. See the request header
;SB struc for the fields you need. If the conventional
;SB sector field is not -1 then a 16 bit sector number
;SB has been specified and we just need to initalise the
;SB high word in cs:Start_Sec_H to 0
;SB
;SB NOTE: START_L and START_H are the offsets withing the IO_REQUEST packet
;SB which contain the low and hi words of the 32 bit start sector if
;SB it has been used.
;SB
;SB NOTE:Remember not to destroy the registers which have been set up before
CMP SI,OFFSET DSKTBL
JNZ DSK_REQ_CONT ; Not Disk Req
CMP DX,-1
JNZ DSK_REQ_16
MOV DX,DS:[BX].START_H ; 32 bits DSK REQ
MOV CS:START_SEC_H,DX ; CS:Start_sec_H = Packet.Start_H
MOV DX,DS:[BX].START_L ; DX = Packet.Start_L
JMP SHORT DSK_REQ_CONT
DSK_REQ_16:
MOV CS:START_SEC_H,0
DSK_REQ_CONT:
;SB34MSB100*********************************************************************
XCHG DI,AX
MOV AL,BYTE PTR DS:[BX].CMD
CMP AL,CS:[SI] ;ARR 2.41
JA CMDERR
CBW ; NOTE THAT AL <= 15 MEANS OK
SHL AX,1
ADD SI,AX
XCHG AX,DI
LES DI,DWORD PTR DS:[BX].TRANS
PUSH CS
POP DS
ASSUME DS:CODE
CLD
JMP WORD PTR [SI+1] ;GO DO COMMAND
DSK$IN ENDP
PAGE
;=====================================================
;=
;= SUBROUTINES SHARED BY MULTIPLE DEVICES
;=
;=====================================================
;----------------------------------------------------------
;
; EXIT - ALL ROUTINES RETURN THROUGH THIS PATH
;
PUBLIC BUS$EXIT
BUS$EXIT PROC FAR
ASSUME DS:NOTHING
MOV AH,00000011B
JMP SHORT ERR1
PUBLIC CMDERR
CMDERR:
MOV AL,3 ;UNKNOWN COMMAND ERROR
PUBLIC ERR$CNT
ERR$CNT:
LDS BX,CS:[PTRSAV]
ASSUME DS:NOTHING
SUB WORD PTR [BX].COUNT,CX ;# OF SUCCESSFUL I/O'S
PUBLIC ERR$EXIT
ERR$EXIT:
MOV AH,10000001B ;MARK ERROR RETURN
JMP SHORT ERR1
BUS$EXIT ENDP
EXITP PROC FAR
ASSUME DS:CODE ; WE ARE NOT SURE THIS IS CORRECT 3/18/86
EXIT$ZER:
LDS BX,[PTRSAV]
ASSUME DS:NOTHING
XOR AX,AX
MOV WORD PTR [BX].COUNT,AX ;INDICATE NO CHARS READ
PUBLIC EXIT
EXIT:
ASSUME DS:NOTHING
MOV AH,00000001B
ERR1:
ASSUME DS:NOTHING
LDS BX,CS:[PTRSAV]
MOV WORD PTR [BX].STATUS,AX ;MARK OPERATION COMPLETE
POP BX
POP ES
POP DS
POP BP
POP DI
POP DX
POP CX
POP AX
POP SI
RET ;RESTORE REGS AND RETURN
EXITP ENDP
;-------------------------------------------------------------
;
; CHROUT - WRITE OUT CHAR IN AL USING CURRENT ATTRIBUTE
;
; CALLED VIA INT 29H
;
PUBLIC CHROUT
CHROUT = 29H
PUBLIC OUTCHR
OUTCHR PROC FAR
PUSH AX
PUSH SI
PUSH DI
PUSH BP
;SB33002a*******************************************************
push bx ; ;SB ;3.30
mov AH, 0Eh ; set command to write a character;SB;3.30
mov BX, 7 ; set foreground color ;SB ;3.30
int 10h ; call rom-bios ;SB ;3.30
pop bx ; ;SB ;3.30
;SB33002a*******************************************************
POP BP
POP DI
POP SI
POP AX
IRET
OUTCHR ENDP
;----------------------------------------------
;
; SET DX TO AUXNUM
;
PUBLIC GETDX
GETDX PROC NEAR
MOV DX,WORD PTR CS:[AUXNUM]
RET
GETDX ENDP
PAGE
;************************************************** ARR 2.15
;-----------------------------------------------
;
; TIMER INTERRUPT HANDLER
;
;TIMER_LOW DW 0
;TIMER_HIGH DW 0
;
;TIMER:
; STI
; PUSH AX
; PUSH CX
; PUSH DX
; PUSH DS
; PUSH CS
; POP DS
; XOR AX,AX
; INT 1AH ; GET ROM TIME AND ZAP ROLL OVER
; MOV [TIMER_HIGH],CX
; MOV [TIMER_LOW],DX
; OR AL,AL
; JZ T5
; INC WORD PTR [DAYCNT] ; ONE DAY GONE BY
;T5:
; POP DS
; POP DX
; POP CX
; POP AX
; IRET
;************************************************** ARR 2.15
CODE ENDS
END

572
v4.0/src/BIOS/MSBIO2.ASM Normal file
View File

@ -0,0 +1,572 @@
PAGE ,132 ;
TITLE MSBIO2 - BIOS
%OUT ...MSBIO2.ASM
;==============================================================================
;REVISION HISTORY:
;AN000 - New for DOS Version 4.00 - J.K.
;AC000 - Changed for DOS Version 4.00 - J.K.
;AN00x - PTM number for DOS Version 4.00 - J.K.
;==============================================================================
;AN001; - P1820 New Message SKL file 10/20/87 J.K.
;AN002; - P5045 New INT 2fh for Get BDS table vector for EMS 06/06/88 J.K.
;==============================================================================
ROMSEGMENT EQU 0F000H
MODELBYTE EQU DS:BYTE PTR [0FFFEH]
MODELPCJR EQU 0FDH
itest=0
INCLUDE MSGROUP.INC ;DEFINE CODE SEGMENT
INCLUDE MSEQU.INC
INCLUDE DEVSYM.INC
INCLUDE PUSHPOP.INC
INCLUDE MSMACRO.INC
ASSUME DS:NOTHING,ES:NOTHING
EXTRN DSK$IN:NEAR
EXTRN SETPTRSAV:NEAR
EXTRN OUTCHR:NEAR
EXTRN SETDRIVE:NEAR
EXTRN FLUSH:NEAR
EXTRN HARDERR:NEAR
EXTRN HARDERR2:NEAR
EXTRN MAPERROR:NEAR
EXTRN GETBP:NEAR
EXTRN CHECKSINGLE:NEAR
EXTRN CHECK_TIME_OF_ACCESS:NEAR
EXTRN EXIT:NEAR
EXTRN HAS1:NEAR
EXTRN READ_SECTOR:NEAR
EXTRN INT_2F_13:FAR
EXTRN OLD13:DWORD
;DATA
EXTRN PTRSAV:DWORD ;IBMBIO1
EXTRN START_BDS:WORD
EXTRN FDRIVE1:WORD
EXTRN FDRIVE2:WORD
EXTRN FDRIVE3:WORD
EXTRN FDRIVE4:WORD
EXTRN FLAGBITS:WORD
EXTRN TIM_DRV:BYTE
EXTRN MEDBYT:BYTE
EXTRN DRVMAX:BYTE
extrn Ext_Boot_Sig:byte ;AN000; ibmbdata
extrn SecPerClusInSector:byte ;AN000; ibmbdata
extrn Boot_Serial_L:word ;AN000; ibmbdata
extrn Boot_Serial_H:word ;AN000; ibmbdata
PATHSTART 005,DISK
EVENB
public Model_Byte
MODEL_BYTE DB 0FFH ; MODEL BYTE. SET UP AT INIT TIME.
; FF - PC1
; FE - XT (64/256K PLANAR)
; FD - PC-JR
; FC - PC/AT
public Secondary_Model_Byte
Secondary_Model_Byte db 0
PUBLIC ORIG19
ORIG19 DD ?
PUBLIC INT19SEM
INT19SEM DB 0 ; INDICATE THAT ALL INT 19
; INITIALIZATION IS COMPLETE
IRP AA,<02,08,09,0A,0B,0C,0D,0E,70,72,73,74,76,77>
public Int19OLD&AA
Int19OLD&AA dd -1 ;Orignal hardware int. vectors for INT 19h.
ENDM
EVENB
PUBLIC DSKDRVS
DSKDRVS DW FDRIVE1
DW FDRIVE2
DW FDRIVE3
DW FDRIVE4
PUBLIC HDSKTAB
HDSKTAB DW HDRIVE
DW DRIVEX
;* Next area is reseved for mini disk BPB pointers *** J.K. 4/7/86
;* Don't change this position. Should be addressible from DskDrvs *** J.K. 4/7/86
MINI_DISK_BPB_PTRS DB 40 dup (?) ;J.K. 4/7/86 - memory reserved for Mini disk.
EVENB
PUBLIC INT_2F_NEXT
INT_2F_NEXT DD ?
RET_ADDR DD ?
PATHEND 005,DISK
; = = = = = = = = = = = = = = = = = = = =
; INT19
;
; WE "HOOK" THE INT 19 VECTOR, BECAUSE CONTRARY TO IBM DOCUMENTATION,
; IT DOES NOT "BOOTSTRAP" THE MACHINE. IT LEAVES MEMORY ALMOST UNTOUCHED.
; SINCE THE BIOS_INIT CODE ASSUMES THAT CERTAIN INTERRUPT VECTORS POINT TO
; THE ROM_BIOS WE MUST "UNHOOK" THEM BEFORE ISSUING THE ACTUAL INT_19.
; CURRENTLY THE ONLY VECTORS THAT NEED TO BE UNHOOKED ARE INT_19, INT_13,
; AND THE HARDWARE INTERRUPTS.
;
PUBLIC INT19
INT19 PROC FAR
XOR AX,AX
MOV DS,AX
assume ds:nothing
assume es:nothing
LES DI,OLD13
MOV DS:[13H*4],DI
MOV DS:[13H*4+2],ES
CMP BYTE PTR INT19SEM, 0
JNZ INT19VECS
JMP DOINT19
; ON THE PCJR, DON'T REPLACE ANY VECTORS
; MODEL BYTE DEFINITIONS FROM IBMSTACK.ASM
MOV AX,ROMSEGMENT
MOV DS,AX
MOV AL,MODELPCJR
CMP AL,MODELBYTE
JNE INT19VECS
JMP DOINT19
;Stacks code has changed these hardware interrupt vectors
;STKINIT in SYSINIT1 will initialzie Int19hOLDxx values.
INT19VECS:
XOR AX,AX
MOV DS,AX
IRP AA,<02,08,09,0A,0B,0C,0D,0E,70,72,73,74,76,77>
LES DI,Int19OLD&AA
;SB33103******************************************************************
mov ax,es ;
cmp ax,-1 ;OPT 0ffffh is unlikely segment
je skip_int&AA ;OPT no need to check selector too
cmp di,-1 ;OPT 0ffffh is unlikely offset
je skip_int&AA
;SB33103******************************************************************
MOV DS:[AA&H*4],DI
MOV DS:[AA&H*4+2],ES
skip_int&AA:
ENDM
DOINT19:
LES DI,ORIG19
MOV DS:[19H*4],DI
MOV DS:[19H*4+2],ES
INT 19H
INT19 ENDP
ASSUME DS:CODE
PUBLIC DSK$INIT
DSK$INIT PROC NEAR
PUSH CS
POP DS
MOV AH,BYTE PTR DRVMAX
MOV DI,OFFSET DSKDRVS
JMP SETPTRSAV
DSK$INIT ENDP
;
; INT 2F HANDLER FOR EXTERNAL BLOCK DRIVERS TO COMMUNICATE WITH THE INTERNAL
; BLOCK DRIVER IN IBMDISK. THE MULTIPLEX NUMBER CHOSEN IS 8. THE HANDLER
; SETS UP THE POINTER TO THE REQUEST PACKET IN [PTRSAV] AND THEN JUMPS TO
; DSK$IN, THE ENTRY POINT FOR ALL DISK REQUESTS.
; ON EXIT FROM THIS DRIVER (AT EXIT), WE WILL RETURN TO THE EXTERNAL DRIVER
; THAT ISSUED THIS INT 2F, AND CAN THEN REMOVE THE FLAGS FROM THE STACK.
; THIS SCHEME ALLOWS US TO HAVE A SMALL EXTERNAL DEVICE DRIVER, AND MAKES
; THE MAINTAINANCE OF THE VARIOUS DRIVERS (DRIVER AND IBMBIO) MUCH EASIER,
; SINCE WE ONLY NEED TO MAKE CHANGES IN ONE PLACE (MOST OF THE TIME).
;
; 06/03/88 J.K. When AL=3, return DS:DI -> Start of BDS table.
; (EMS device driver hooks INT 13h to handle 16KB DMA overrun
; problem. BDS table is going to be used to get head/sector
; informations without calling Generic IOCTL Get Device Parm call.)
;
; AL CONTAINS THE INT2F FUNCTION:
; 0 - CHECK FOR INSTALLED HANDLER - RESERVED
; 1 - INSTALL THE BDS INTO THE LINKED LIST
; 2 - DOS REQUEST
; 3 - Get BDS vector ;06/03/88 J.K.
; Return BDS table starting pointer in DS:DI
MYNUM EQU 8
PUBLIC INT2F_DISK
INT2F_DISK PROC FAR
CMP AH,MYNUM
JE MINE
JMP CS:[INT_2F_NEXT] ; CHAIN TO NEXT INT 2F HANDLER
MINE:
CMP AL,0F8H ; IRET ON RESERVED FUNCTIONS
JB DO_FUNC
IRET
DO_FUNC:
OR AL,AL ; A GET INSTALLED STATE REQUEST?
JNE DISP_FUNC
MOV AL,0FFH
IRET
DISP_FUNC:
MESSAGE FTESTINIT,<"INT2F_DISK",CR,LF>
CMP AL,1 ; REQUEST FOR INSTALLING BDS?
JNE DO_DOS_REQ
CALL INSTALL_BDS
IRET
DO_DOS_REQ:
; SET UP POINTER TO REQUEST PACKET
cmp al, 3 ;AN002; Get BDS vector?
je DO_Get_BDS_Vector ;AN002;
MOV WORD PTR CS:[PTRSAV],BX ;othrwise DOS function.
MOV WORD PTR CS:[PTRSAV+2],ES
JMP DSK$IN
DO_Get_BDS_Vector: ;AN002; AL=3
push cs ;AN002;
pop ds ;AN002;
mov di, Start_BDS ;AN002;
IRET ;AN002;
INT2F_DISK ENDP
;
; INSTALL_BDS INSTALLS A BDS A LOCATION DS:DI INTO THE CURRENT LINKED LIST OF
; BDS MAINTAINED BY THIS DEVICE DRIVER. IT PLACES THE BDS AT THE END OF THE
; LIST.
PUBLIC INSTALL_BDS
INSTALL_BDS PROC NEAR
MESSAGE FTESTINIT,<"INSTALL BDS",CR,LF>
; DS:DI POINT TO BDS TO BE INSTALLED
LES SI,DWORD PTR CS:[START_BDS] ; START AT BEGINNING OF LIST
PUSH ES ; SAVE POINTER TO CURRENT BDS
PUSH SI
; ES:SI NOW POINT TO BDS IN LINKED LIST
LOOP_NEXT_BDS:
CMP SI,-1 ; GOT TO END OF LINKED LIST?
JZ INSTALL_RET
; IF WE HAVE SEVERAL LOGICAL DRIVES USING THE SAME PHYSICAL DRIVE, WE MUST
; SET THE I_AM_MULT FLAG IN EACH OF THE APPROPRIATE BDSS.
MOV AL,BYTE PTR DS:[DI].DRIVENUM
CMP BYTE PTR ES:[SI].DRIVENUM,AL
JNZ NEXT_BDS
MESSAGE FTESTINIT,<"LOGICAL DRIVES",CR,LF>
XOR BX,BX
MOV BL,FI_AM_MULT
OR WORD PTR DS:[DI].FLAGS,BX ; SET FLAGS IN BOTH BDSS CONCERNED
OR WORD PTR ES:[SI].FLAGS,BX
MOV BL,FI_OWN_PHYSICAL
XOR BX,-1
AND WORD PTR DS:[DI].FLAGS,BX ; RESET THAT FLAG FOR 'NEW' BDS
; WE MUST ALSO SET THE FCHANGELINE BIT CORRECTLY.
MOV BX,WORD PTR ES:[SI].FLAGS ; DETERMINE IF CHANGELINE AVAILABLE
AND BL,FCHANGELINE
XOR BH,BH
OR WORD PTR DS:[DI].FLAGS,BX
NEXT_BDS:
; BEFORE MOVING TO NEXT BDS, PRESERVE POINTER TO CURRENT ONE. THIS IS NEEDED AT
; THE END WHEN THE NEW BDS IS LINKED INTO THE LIST.
POP BX ; DISCARD PREVIOUS POINTER TO BDS
POP BX
PUSH ES
PUSH SI
MOV BX,WORD PTR ES:[SI].LINK + 2
MOV SI,WORD PTR ES:[SI].LINK
MOV ES,BX
JMP SHORT LOOP_NEXT_BDS
INSTALL_RET:
POP SI ; RETRIEVE POINTER TO LAST BDS
POP ES ; IN LINKED LIST.
MOV AX,DS
MOV WORD PTR ES:[SI].LINK+2,AX ; INSTALL BDS
MOV WORD PTR ES:[SI].LINK,DI
MOV WORD PTR DS:[DI].LINK,-1 ; SET NEXT POINTER TO NULL
RET
INSTALL_BDS ENDP
;
; RE_INIT INSTALLS THE INT 2F VECTOR THAT WILL HANDLE COMMUNICATION BETWEEN
; EXTERNAL BLOCK DRIVERS AND THE INTERNAL DRIVER. IT ALSO INSTALLS THE
; RESET_INT_13 INTERFACE. IT IS CALLED BY SYSYINIT
;
PUBLIC RE_INIT
RE_INIT PROC FAR
MESSAGE FTESTINIT,<"REINIT",CR,LF>
PUSH AX
PUSH DS
PUSH DI
XOR DI,DI
MOV DS,DI
MOV DI,2FH*4 ; POINT IT TO INT 2F VECTOR
MOV AX,WORD PTR DS:[DI]
MOV WORD PTR CS:[INT_2F_NEXT],AX
MOV AX,WORD PTR DS:[DI+2] ; PRESERVE OLD INT 2F VECTOR
MOV WORD PTR CS:[INT_2F_NEXT+2],AX
; INSTALL THE RESET_INT_13
; INTERFACE
;
; THE FOLLOWING TWO LINES ARE NOT NEEDED ANYMORE BECAUSE THE LINK HAS BEEN
; HARD-WIRED INTO THE CODE AT NEXT2F_13. - RAJEN.
;------------------------------------------------------------------------------
; MOV WORD PTR CS:[NEXT2F_13],OFFSET INT2F_DISK ; PRESERVE INT2F_DISK POINTER
; MOV WORD PTR CS:[NEXT2F_13+2],CS
;------------------------------------------------------------------------------
CLI
MOV WORD PTR DS:[DI],OFFSET INT_2F_13 ; INSTALL NEW VECTORS
MOV WORD PTR DS:[DI+2],CS
STI
POP DI
POP DS
POP AX
RET
RE_INIT ENDP
;-------------------------------------------------
;
; ASK TO SWAP THE DISK IN DRIVE A:
;
PUBLIC SWPDSK
SWPDSK PROC NEAR
MOV AL,BYTE PTR DS:[DI].DRIVELET ; GET THE DRIVE LETTER
;USING A DIFFERENT DRIVE IN A ONE DRIVE SYSTEM SO REQUEST THE USER CHANGE DISKS
ADD AL,"A"
MOV CS:DRVLET,AL
PUSH DS ; PRESERVE SEGMENT REGISTER
PUSH CS
POP DS
MOV SI,OFFSET SNGMSG ; DS:SI -> MESSAGE
PUSH BX
CALL WRMSG ;PRINT DISK CHANGE MESSAGE
CALL FLUSH
;SB33003***************************************************************
xor AH, AH ; set command to read character;SB
int 16h ; call rom-bios ;SB
;SB33003***************************************************************
POP BX
POP DS ; RESTORE SEGMENT REGISTER
WRMRET:
RET
SWPDSK ENDP
;----------------------------------------------
;
; WRITE OUT MESSAGE POINTED TO BY [SI]
;
PUBLIC WRMSG
WRMSG PROC NEAR
LODSB ;GET THE NEXT CHARACTER OF THE MESSAGE
OR AL,AL ;SEE IF END OF MESSAGE
JZ WRMRET
; INT CHROUT
PUSHF
PUSH CS
CALL OUTCHR
JMP SHORT WRMSG
WRMSG ENDP
; INCLUDE BIOMES.INC
include MSBIO.CL2
;
; END OF SUPPORT FOR MULTIPLE FLOPPIES WITH NO LOGICAL DRIVES
; THIS IS NOT 'SPECIAL' ANY MORE BECAUSE WE NOW HAVE THE CAPABILITY OF
; DEFINING LOGICAL DRIVES IN CONFIG.SYS. WE THEREFORE KEEP THE CODE FOR
; SWAPPING RESIDENT ALL THE TIME.
;
;J.K. 10/1/86 *******************************************************
;Variables for Dynamic Relocatable modules
;These should be stay resident.
public INT6C_RET_ADDR
INT6C_RET_ADDR DD ? ; return address from INT 6C for P12 machine
PATHSTART 001,CLK
;
; DATA STRUCTURES FOR REAL-TIME DATE AND TIME
;
public BIN_DATE_TIME
public MONTH_TABLE
public DAYCNT2
public FEB29
BIN_DATE_TIME:
DB 0 ; CENTURY (19 OR 20) OR HOURS (0-23)
DB 0 ; YEAR IN CENTURY (0...99) OR MINUTES (0-59)
DB 0 ; MONTH IN YEAR (1...12) OR SECONDS (0-59)
DB 0 ; DAY IN MONTH (1...31)
MONTH_TABLE: ;
DW 0 ;MJB002 JANUARY
DW 31 ;MJB002 FEBRUARY
DW 59 ;MJB002
DW 90 ;MJB002
DW 120 ;MJB002
DW 151 ;MJB002
DW 181 ;MJB002
DW 212 ;MJB002
DW 243 ;MJB002
DW 273 ;MJB002
DW 304 ;MJB002
DW 334 ;MJB002 DECEMBER
DAYCNT2 DW 0000 ;MJB002 TEMP FOR COUNT OF DAYS SINCE 1-1-80
FEB29 DB 0 ;MJB002 FEBRUARY 29 IN A LEAP YEAR FLAG
PATHEND 001,CLK
;********************************************************************
;
PUBLIC ENDFLOPPY
ENDFLOPPY LABEL BYTE
;
; END OF CODE FOR VIRTUAL FLOPPY DRIVES
;
PUBLIC ENDSWAP
ENDSWAP LABEL BYTE
PATHSTART 004,BIO
PUBLIC HNUM
HNUM DB 0 ;NUMBER OF HARDFILES
PUBLIC HARDDRV
HARDDRV DB 80H ;PHYSICAL DRIVE NUMBER OF FIRST HARDFILE
;**********************************************************************
; "HDRIVE" IS A HARD DISK WITH 512 BYTE SECTORS
;*********************************************************************
EVENB
PUBLIC BDSH
BDSH DW -1 ;LINK TO NEXT STRUCTURE
DW CODE
DB 80 ;INT 13 DRIVE NUMBER
DB "C" ;LOGICAL DRIVE LETTER
PUBLIC HDRIVE
HDRIVE:
DW 512
DB 1 ;SECTORS/ALLOCATION UNIT
DW 1 ;RESERVED SECTORS FOR DOS
DB 2 ;NO. OF ALLOCATION TABLES
DW 16 ;NUMBER OF DIRECTORY ENTRIES
DW 0000 ;NUMBER OF SECTORS (AT 512 BYTES EACH)
DB 11111000B ;MEDIA DESCRIPTOR
DW 1 ;NUMBER OF FAT SECTORS
DW 00 ;SECTOR LIMIT
DW 00 ;HEAD LIMIT
DW 00 ;HIDDEN SECTOR COUNT(low)
dw 00 ;AN000; Hidden Sector (high)
dw 00 ;AN000; Number of Sectors (low)
dw 00 ;AN000; Number of Sectors (high)
DB 0 ; TRUE => BIGFAT
OPCNTH DW 0 ;OPEN REF. COUNT
DB 3 ;FORM FACTOR
FLAGSH DW 0020H ;VARIOUS FLAGS
; DB 9 DUP (0) ;RESERVED FOR FUTURE USE
DW 40 ; NUMBER OF CYLINDERS
RECBPBH DB 31 DUP (?) ; RECOMMENDED BPB FOR DRIVE
TRACKH DB -1 ;LAST TRACK ACCESSED ON THIS DRIVE
TIM_LOH DW -1 ;KEEP THESE TWO CONTIGUOUS (?)
TIM_HIH DW -1
VOLIDH DB "NO NAME ",0 ;AN000; VOLUME ID FOR THIS DISK
VolSerH dd 0 ;AN000; Current volume serial number from Boot record
SysIDH db "FAT12 " ,0 ;AN000; Current file system id from Boot record
;
; END OF SINGLE HARD DISK SECTION
;
PUBLIC ENDONEHARD
ENDONEHARD LABEL BYTE
;**********************************************************************
; "DRIVEX " IS AN EXTRA TYPE OF DRIVE USUALLY RESERVED FOR AN
; ADDITIONAL HARD FILE
;*********************************************************************
EVENB
PUBLIC BDSX
BDSX DW -1 ;LINK TO NEXT STRUCTURE
DW CODE
DB 81 ;INT 13 DRIVE NUMBER
DB "D" ;LOGICAL DRIVE LETTER
PUBLIC DRIVEX
DRIVEX:
DW 512
DB 00 ;SECTORS/ALLOCATION UNIT
DW 1 ;RESERVED SECTORS FOR DOS
DB 2 ;NO. OF ALLOCATION TABLES
DW 0000 ;NUMBER OF DIRECTORY ENTRIES
DW 0000 ;NUMBER OF SECTORS (AT 512 BYTES EACH)
DB 11111000B ;MEDIA DESCRIPTOR
DW 0000 ;NUMBER OF FAT SECTORS
DW 00 ;SECTOR LIMIT
DW 00 ;HEAD LIMIT
DW 00 ;HIDDEN SECTOR COUNT (low)
dw 00 ;AN000; Hidden Sector (high)
dw 00 ;AN000; Number of Sectors (low)
dw 00 ;AN000; Number of Sectors (high)
DB 0 ; TRUE => BIGFAT
OPCNTD DW 0 ;OPEN REF. COUNT
DB 3 ;FORM FACTOR
FLAGSD DW 0020H ;VARIOUS FLAGS
; DB 9 DUP (0) ;RESERVED FOR FUTURE USE
DW 40 ; NUMBER OF CYLINDERS
RECBPBD DB 31 DUP (?) ; RECOMMENDED BPB FOR DRIVE
TRACKD DB -1 ;LAST TRACK ACCESSED ON THIS DRIVE
TIM_LOD DW -1 ;KEEP THESE TWO CONTIGUOUS (?)
TIM_HID DW -1
VOLIDD DB "NO NAME ",0 ;AN000; VOLUME ID FOR THIS DISK
VolSerD dd 0 ;AN000; Current volume serial number from Boot record
SysIDD db "FAT12 " ,0 ;AN000; Current file system id from Boot record
;
; END OF SECTION FOR TWO HARD DISKS
PUBLIC ENDTWOHARD
ENDTWOHARD LABEL BYTE
PATHEND 004,BIO
PUBLIC TWOHARD
TWOHARD LABEL BYTE
PAGE
INCLUDE MS96TPI.INC
;*********************************************************************
;Memory allocation for BDSM table. - J.K. 2/21/86
;*********************************************************************
PUBLIC BDSMs
BDSMs BDSM_type Max_mini_dsk_num dup (<>) ;currently max. 23
;** End_of_BDSM defined in IBMINIT.ASM will be used to set the appropriate
;** ending address of BDSM table.
;
;;3.3 BUG FIX -SP ------------------------------
;;Migrated into 4.00 -MRW
;Paragraph buffer between the BDSMs and MSHARD
;
;The relocation code for MSHARD needs this. this cannot be used for
;anything. nothing can come before this or after this.....IMPORTANT!!!!
;don't get too smart and using this buffer for anything!!!!!!
;
db 16 dup(0)
;
;end of bug fix buffer
;;
;;3.3 BUG FIX -SP------------------------------
CODE ENDS
END

296
v4.0/src/BIOS/MSCLOCK.ASM Normal file
View File

@ -0,0 +1,296 @@
TITLE MSCLOCK - DOS 3.3
;----------------------------------------------------------------
; :
; CLOCK DEVICE DRIVER :
; :
; :
; This file contains the Clock Device Driver. :
; :
; The routines in this files are: :
; :
; routine function :
; ------- -------- :
; TIM$WRIT Set the current time :
; TIM$READ Read the current time :
; Time_To_Ticks Convert time to corresponding :
; number of clock ticks :
; :
; The clock ticks at the rate of: :
; :
; 1193180/65536 ticks/second (about 18.2 ticks per second):
; See each routine for information on the use. :
; :
;----------------------------------------------------------------
itest=0
INCLUDE MSGROUP.INC ;DEFINE CODE SEGMENT
INCLUDE MSMACRO.INC
EXTRN EXIT:NEAR
;
; DAYCNT is the number of days since 1-1-80.
; Each time the clock is read it is necessary to check if another day has
; passed. The ROM only returns the day rollover once so if it is missed
; the time will be off by a day.
;
EXTRN DAYCNT:WORD ;MSDATA
;;Rev 3.30 Modification ------------------------------------------------
; variables for real time clock setting
public HaveCMOSClock
HaveCMOSClock db 0 ;set by MSINIT.
public base_century
base_century db 19
public base_year
base_year db 80
public month_tab
month_tab db 31,28,31,30,31,30,31,31,30,31,30,31
; The following are indirect intra-segment call addresses. The
;procedures are defined in MSINIT for relocation. MSINIT will set these
;address when the relocation is done.
public BinToBCD
BinToBCD dw 0 ;should point to Bin_To_BCD proc in MSINIT
public DaycntToDay
DaycntToDay dw 0 ;should point to Daycnt_to_day in MSINIT
;********************************************************************
; Indirect call address of TIME_TO_TICKS procedure.
;This will be used by the relocatable portable suspend/resume code.
public TimeToTicks
TimeToTicks dw Time_To_Ticks
;;End of Modification ------------------------------------------------
;--------------------------------------------------------------------
;
; Settime sets the current time
;
; On entry ES:[DI] has the current time:
;
; number of days since 1-1-80 (WORD)
; minutes (0-59) (BYTE)
; hours (0-23) (BYTE)
; hundredths of seconds (0-99) (BYTE)
; seconds (0-59) (BYTE)
;
; Each number has been checked for the correct range.
;
PUBLIC TIM$WRIT
TIM$WRIT PROC NEAR
ASSUME DS:CODE
mov AX,WORD PTR ES:[DI]
push AX ;DAYCNT. We need to set this at the very
; end to avoid tick windows.
;;Rev 3.30 Modification
cmp HaveCMOSClock, 0
je No_CMOS_1
mov al,es:[di+3] ;get binary hours
call BinToBCD ;convert to BCD
mov ch,al ;CH = BCD hours
mov al,es:[di+2] ;get binary minutes
call BinToBCD ;convert to BCD
mov cl,al ;CL = BCD minutes
mov al,es:[di+5] ;get binary seconds
call BinToBCD ;convert to BCD
mov dh,al ;DH = BCD seconds
mov dl,0 ;DL = 0 (ST) or 1 (DST)
cli ;turn off timer
mov ah,03h ;set RTC time
int 1Ah ;call rom bios clock routine
sti
;;End of Modification
No_CMOS_1:
mov CX,WORD PTR ES:[DI+2]
mov DX,WORD PTR ES:[DI+4]
;;Rev 3.30 Modification
call time_to_ticks ; convert time to ticks
;CX:DX now has time in ticks
cli ; Turn off timer
mov AH, 1 ; command is set time in clock
int 1Ah ; call rom-bios clock routines
pop [DAYCNT]
sti
;CMOS clock -------------------------------------
cmp HaveCMOSClock, 0
je No_CMOS_2
call DaycntToDay ; convert to BCD format
cli ; Turn off timer
mov AH,05h ; set RTC date
int 1Ah ; call rom-bios clock routines
sti
;------------------------------------------------
No_CMOS_2:
jmp EXIT
TIM$WRIT ENDP
;;End of Modification
;
; convert time to ticks
; input : time in CX and DX
; ticks returned in CX:DX
;
public time_to_ticks
TIME_TO_TICKS PROC NEAR
; first convert from Hour,min,sec,hund. to
; total number of 100th of seconds
mov AL,60
mul CH ;Hours to minutes
mov CH,0
add AX,CX ;Total minutes
mov CX,6000 ;60*100
mov BX,DX ;Get out of the way of the multiply
mul CX ;Convert to 1/100 sec
mov CX,AX
mov AL,100
mul BH ;Convert seconds to 1/100 sec
add CX,AX ;Combine seconds with hours and min.
adc DX,0 ;Ripple carry
mov BH,0
add CX,BX ;Combine 1/100 sec
adc DX,0
;;Rev 3.30 Modification
;DX:CX IS TIME IN 1/100 SEC
XCHG AX,DX
XCHG AX,CX ;NOW TIME IS IN CX:AX
MOV BX,59659
MUL BX ;MULTIPLY LOW HALF
XCHG DX,CX
XCHG AX,DX ;CX->AX, AX->DX, DX->CX
MUL BX ;MULTIPLY HIGH HALF
ADD AX,CX ;COMBINE OVERLAPPING PRODUCTS
ADC DX,0
XCHG AX,DX ;AX:DX=TIME*59659
MOV BX,5
DIV BL ;DIVIDE HIGH HALF BY 5
MOV CL,AL
MOV CH,0
MOV AL,AH ;REMAINDER OF DIVIDE-BY-5
CBW
XCHG AX,DX ;USE IT TO EXTEND LOW HALF
DIV BX ;DIVDE LOW HALF BY 5
MOV DX,AX
; CX:DX is now number of ticks in time
ret
TIME_TO_TICKS ENDP
;;End of Modification
;
; Gettime reads date and time
; and returns the following information:
;
; ES:[DI] =count of days since 1-1-80
; ES:[DI+2]=hours
; ES:[DI+3]=minutes
; ES:[DI+4]=seconds
; ES:[DI+5]=hundredths of seconds
;
PUBLIC TIM$READ
TIM$READ PROC NEAR
; read the clock
xor AH, AH ; set command to read clock
int 1Ah ; call rom-bios to get time
or al,al ; check for a new day
jz noroll1 ; if al=0 then don't reset day count
INC [DAYCNT] ; CATCH ROLLOVE
noroll1:
MOV SI,[DAYCNT]
;
; we now need to convert the time in tick to the time in 100th of
; seconds. The relation between tick and seconds is:
;
; 65536 seconds
; ----------------
; 1,193,180 tick
;
; To get to 100th of second we need to multiply by 100. The equation is:
;
; Ticks from clock * 65536 * 100
; --------------------------------- = time in 100th of seconds
; 1,193,180
;
; Fortunately this fromula simplifies to:
;
; Ticks from clock * 5 * 65,536
; --------------------------------- = time in 100th of seconds
; 59,659
;
; The calculation is done by first multipling tick by 5. Next we divide by
; 59,659. In this division we multiply by 65,536 by shifting the dividend
; my 16 bits to the left.
;
; start with ticks in CX:DX
; multiply by 5
MOV AX,CX
MOV BX,DX
SHL DX,1
RCL CX,1 ;TIMES 2
SHL DX,1
RCL CX,1 ;TIMES 4
ADD DX,BX
ADC AX,CX ;TIMES 5
XCHG AX,DX
; now have ticks * 5 in DX:AX
; we now need to multiply by 65,536 and divide by 59659 d.
mov CX,59659 ; get divisor
div CX
; DX now has remainder
; AX has high word of final quotient
mov BX,AX ; put high work if safe place
xor AX,AX ; this is the multiply by 65536
div CX ; BX:AX now has time in 100th of seconds
;
;Rounding based on the remainder may be added here
;The result in BX:AX is time in 1/100 second.
mov DX,BX
mov CX,200 ;Extract 1/100's
;Division by 200 is necessary to ensure no overflow--max result
;is number of seconds in a day/2 = 43200.
div CX
cmp DL,100 ;Remainder over 100?
jb NOADJ
sub DL,100 ;Keep 1/100's less than 100
NOADJ:
cmc ;If we subtracted 100, carry is now set
mov BL,DL ;Save 1/100's
;To compensate for dividing by 200 instead of 100, we now multiply
;by two, shifting a one in if the remainder had exceeded 100.
rcl AX,1
mov DL,0
rcl DX,1
mov CX,60 ;Divide out seconds
div CX
mov BH,DL ;Save the seconds
div CL ;Break into hours and minutes
xchg AL,AH
;Time is now in AX:BX (hours, minutes, seconds, 1/100 sec)
push AX
MOV AX,SI ; DAYCNT
stosw
pop AX
stosw
mov AX,BX
stosw
jmp EXIT
TIM$READ ENDP
CODE ENDS
END


328
v4.0/src/BIOS/MSCON.ASM Normal file
View File

@ -0,0 +1,328 @@
PAGE ,132 ;
TITLE MSCON - BIOS
%OUT ...MSCON.ASM
;==============================================================================
;REVISION HISTORY:
;AN000 - New for DOS Version 4.00 - J.K.
;AC000 - Changed for DOS Version 4.00 - J.K.
;AN00x - PTM number for DOS Version 4.00 - J.K.
;==============================================================================
itest=0
INCLUDE MSGROUP.INC ;DEFINE CODE SEGMENT
INCLUDE JUMPMAC.INC
INCLUDE MSEQU.INC
INCLUDE MSMACRO.INC
;*** DOS 3.3 will not support more than 25 rows
; INCLUDE DEVSYM.INC ;J.K. 4/29/86 for CON$GENIOCTL support
; INCLUDE IOCTL.INC ;J.K. 4/29/86 for CON$GENIOCTL support
EXTRN EXIT:NEAR ;MSBIO1
EXTRN BUS$EXIT:NEAR ;MSBIO1
; EXTRN CMDERR:NEAR ;MSBIO1 J.K. 4/29/86
;DATA
EXTRN PTRSAV:DWORD ;MSBIO1
EXTRN FHAVEK09:BYTE ;MSDISK
EXTRN ALTAH:BYTE ;MSBDATA
EXTRN KEYRD_Func:Byte ;MSBDATA
EXTRN KEYSTS_Func:Byte ;MSBDATA
; EXTRN SAV_SC_INFO:BYTE ;MSBDATA J.K. 4/29/86
; EXTRN SAV_SC_MODE:BYTE ;MSBDATA J.K. 4/29/86
;------------------------------------------------------
;
; CONSOLE READ ROUTINE
;
ASSUME DS:CODE ; THIS WAS SET BY THE CON DD ENTRY POINT
PUBLIC CON$READ
CON$READ PROC NEAR
JCXZ CON$EXIT
CON$LOOP:
CALL CHRIN ;GET CHAR IN AL
STOSB ;STORE CHAR AT ES:DI
LOOP CON$LOOP
CON$EXIT:
JUMP EXIT
CON$READ ENDP
;---------------------------------------------------------
;
; INPUT SINGLE CHAR INTO AL
;
;J.K.5/12/87 We are going to issue extended keyboard function, if supported.
;The returning value of the extended key stroke of the extended key board
;function uses 0E0h in AL instead of 00 as in the conventional key board
;function. This creates a conflict when the user entered real Greek Alpha
;charater (= 0E0h) to distinguish the extended key stroke and the Greek Alpha.
;This case will be handled in the following manner;
; AH = 16h
; INT 16h
; If AL == 0, then extended code (in AH)
; else If AL == 0E0h, then
; IF AH <> 0, then extended code (in AH)
; else Greek_Alpha character.
;Also, for compatibility reason, if an extended code is detected, then we
;are going to change the value in AL from 0E0h to 00h.
CHRIN PROC NEAR
;AN000;
; XOR AX,AX
mov ah,KEYRD_Func ;AN000; Set by MSINIT. 0 or 10h
xor al,al ;AN000;
XCHG AL,ALTAH ;GET CHARACTER & ZERO ALTAH
OR AL,AL
JNZ KEYRET
;SB34CON000**************************************************************
;SB Keyboard I/O interrupt
;SB AH already contains the keyboard read function number
;SB 1 LOC
int 16h
;SB34CON000**************************************************************
ALT10:
OR AX,AX ;CHECK FOR NON-KEY AFTER BREAK
JZ CHRIN
CMP AX,7200H ;CHECK FOR CTRL-PRTSC
JNZ ALT_Ext_Chk ;AN000;
MOV AL,16
jmp KeyRet ;AN000;
ALT_Ext_Chk:
;SB34CON001**************************************************************
;SB IF operation was extended function (i.e. KEYRD_Func != 0) THEN
;SB IF character read was 0E0h THEN
;SB IF extended byte was zero (i.e. AH == 0) THEN
;SB goto keyret
;SB ELSE
;SB set AL to zero
;SB goto ALT_SAVE
;SB ENDIF
;SB ENDIF
;SB ENDIF
;SB 9 LOCS
cmp BYTE PTR KEYRD_Func,0
jz NOT_EXT
cmp al,0E0h
jnz NOT_EXT
or ah,ah
jz KEYRET
xor al,al
jmp short ALT_SAVE
NOT_EXT:
;SB34CON001**************************************************************
OR AL,AL ;SPECIAL CASE?
JNZ KEYRET
ALT_SAVE:
MOV ALTAH,AH ;STORE SPECIAL KEY
KEYRET:
RET
CHRIN ENDP
;--------------------------------------------------------------
;
; KEYBOARD NON DESTRUCTIVE READ, NO WAIT
;
; PC-CONVERTIBLE-TYPE MACHINE: IF BIT 10 IS SET BY THE DOS IN THE STATUS WORD
; OF THE REQUEST PACKET, AND THERE IS NO CHARACTER IN THE INPUT BUFFER, THE
; DRIVER ISSUES A SYSTEM WAIT REQUEST TO THE ROM. ON RETURN FROM THE ROM, IT
; RETURNS A 'CHAR-NOT-FOUND' TO THE DOS.
;
CONBUSJ:
ASSUME DS:NOTHING
JMP CONBUS
ASSUME DS:CODE ; THIS WAS SET BY THE CON DD ENTRY POINT
PUBLIC CON$RDND
CON$RDND:
MOV AL,[ALTAH]
OR AL,AL
JZ RD1
JMP RDEXIT
RD1:
;SB34CON002**************************************************************
;SB Keyboard I/O interrupt
;SB Get keystroke status (KEYSTS_Func)
;SB 2 LOCS
mov ah,KEYSTS_Func
int 16h
;SB34CON002**************************************************************
JZ NOCHR
JMP GOTCHR
NOCHR:
CMP FHAVEK09,0
JZ CONBUSJ
LDS BX,[PTRSAV]
ASSUME DS:NOTHING
TEST [BX].STATUS,0400H ; SYSTEM WAIT ENABLED?
JZ CONBUSJ
;********************************
; NEED TO WAIT FOR IBM RESPONSE TO REQUEST FOR CODE ON HOW TO USE THE SYSTEM
; WAIT CALL.
;********************************
MESSAGE FTESTCON,<"SYSTEM WAIT STAGE",CR,LF>
MOV AX,4100H ; WAIT ON AN EXTERNAL EVENT
; MOV BX,0300H ; NO TIMEOUT
; MOV DX,60H ; LOOK AT I/O PORT 60H
INT 15H ; CALL ROM FOR SYSTEM WAIT
MESSAGE FTESTCON,<"OUT OF WAIT. AX IS ">
MNUM FTESTCON,AX
MESSAGE FTESTCON,<CR,LF>
JMP CONBUS
ASSUME DS:CODE
GOTCHR:
OR AX,AX
JNZ NOTBRK ;CHECK FOR NULL AFTER BREAK
;SB34CON004**************************************************************
;SB Keyboard I/O interrupt
;SB Keyboard read function (KEYRD_Func)
;SB 2 LOCS
mov ah,KEYRD_Func
int 16h
;SB34CON004**************************************************************
JUMP CON$RDND ;AND GET A REAL STATUS
NOTBRK:
CMP AX,7200H ;CHECK FOR CTRL-PRTSC
JNZ RD_Ext_Chk ;AN000;
MOV AL,16
jmp RDEXIT ;AN000;
RD_Ext_Chk: ;AN000;
cmp KEYRD_Func, 0 ;AN000; Extended Keyboard function?
jz RDEXIT ;AN000; No. Normal exit.
cmp al,0E0h ;AN000; Extended key value or Greek Alpha?
jne RDEXIT ;AN000;
cmp ah, 0 ;AN000; Scan code exist?
jz RDEXIT ;AN000; Yes. Greek Alpha char.
mov al, 0 ;AN000; No. Extended key stroke. Change it for compatibility
PUBLIC RDEXIT
RDEXIT:
LDS BX,[PTRSAV]
ASSUME DS:NOTHING
MOV [BX].MEDIA,AL
EXVEC:
JUMP EXIT
CONBUS:
ASSUME DS:NOTHING
JUMP BUS$EXIT
;--------------------------------------------------------------
;
; KEYBOARD FLUSH ROUTINE
;
ASSUME DS:CODE ; THIS WAS SET BY THE CON DD ENTRY POINT
PUBLIC CON$FLSH
CON$FLSH:
CALL FLUSH
JUMP EXIT
PUBLIC FLUSH
FLUSH:
MOV [ALTAH],0 ;CLEAR OUT HOLDING BUFFER
FLLOOP:
;SB33012****************************************************************
;SB ; Is there a char there?
mov AH, 1 ;SB ; command code for check status
int 16h ;SB ; call rom-bios keyboard routine
;SB33012****************************************************************
JZ FLDONE
;SB33013****************************************************************
xor AH, AH ;SB ; if zf is nof set, get character
int 16h ;SB ; call rom-bios to get character
;SB33013****************************************************************
JMP FLLOOP
FLDONE:
RET
;----------------------------------------------------------
;
; CONSOLE WRITE ROUTINE
;
ASSUME DS:CODE ; THIS WAS SET BY THE CON DD ENTRY POINT
PUBLIC CON$WRIT
CON$WRIT:
JCXZ EXVEC
CON$LP:
MOV AL,ES:[DI] ;GET CHAR
INC DI
INT CHROUT ;OUTPUT CHAR
LOOP CON$LP ;REPEAT UNTIL ALL THROUGH
JUMP EXIT
;-----------------------------------------------
;
; BREAK KEY HANDLING
;
PUBLIC CBREAK
CBREAK:
MOV CS:ALTAH,3 ;INDICATE BREAK KEY SET
PUBLIC INTRET
INTRET:
IRET
;------------------------------------------------------------------------------
;J.K. 4/29/86 - CONSOLE GENERIC IOCTL SUPPORT FOR DOS 3.3.
;CON$GENIOCTL supports Get mode information, Set mode information functions.
;It will only save the value from "Set mode information" and will return
;the value through "Get mode information". It is supposed to be set by
;the MODE.COM and other application program can retrieve information
;through "Get mode information" call.
;Initially, there is no valuable informaton until set by MODE command, so
;any attemp to "Get mode information" at that points will fail. (unknown
;command with carry set.)
;At entry: CS = DS = code
; CS:[PTRSAV] has seg, address of the Request Header saved in
; in Strategy routine.
;
; PUBLIC CON$GENIOCTL
; ASSUME DS:CODE
;CON$GENIOCTL:
; les di, CS:[PTRSAV] ;get the request header
; cmp es:[di].MajorFunction, IOC_SC
; je Major_SC_OK
;SC_CMDERR:
; stc
; jmp cmderr ;carry is set, exit to cmderr
;Major_SC_OK:
; mov al, es:[di].MinorFunction ;save minor function
; les di, es:[di].GenericIOCTL_Packet ;pointer of SC_MODE_INFO structure
; mov cx, es:[di].SC_INFO_LENGTH ;save length
; inc di
; inc di ;ES:DI -> SC_MODE in Info. Packet
; cmp cx, SC_INFO_PACKET_LENGTH ;currently 9.
; jne SC_CMDERR ;cannot accept the different packet
; cmp al, GET_SC_MODE ;minor function = 60h ?
; jne SC_SET_MODE_FUNC ;no, check if it is "Set mode function"
; cmp SAV_SC_MODE, 0 ;information set before?
; je SC_CMDERR ;no, cannot get the info.
;;SC_GET_MODE_FUNC: ;es:di -> SC_MODE in info. packet
; ;cx - length
; mov si, offset SAV_SC_INFO
; rep movsb ;ds:si -> sav_sc_info, es:di -> sc_mode
; jmp exit
;
;SC_SET_MODE_FUNC: ;es:di -> SC_MODE
; cmp al, SET_SC_MODE ;minor function = 40h ?
; jne SC_CMDERR
; mov si, offset SAV_SC_INFO
; xchg di, si
; push es
; push ds
; pop es
; pop ds
; rep movsb ;ds:si -> sc_mode, es:di -> sav_sc_info
; jmp exit
;
;J.K. 4/29/86 - End of CONSOLE GENERIC IOCTL SUPPORT FOR DOS 3.3.
CODE ENDS
END

2443
v4.0/src/BIOS/MSDISK.ASM Normal file

File diff suppressed because it is too large Load Diff

22
v4.0/src/BIOS/MSDSKPR.INC Normal file
View File

@ -0,0 +1,22 @@
; The following structure defines the disk parameter table
; pointed to by Interrupt vector 1EH (location 0:78H)
DISK_PARMS STRUC
DISK_SPECIFY_1 DB ?
DISK_SPECIFY_2 DB ?
DISK_MOTOR_WAIT DB ? ; Wait till motor off
DISK_SECTOR_SIZ DB ? ; Bytes/Sector (2 = 512)
DISK_EOT DB ? ; Sectors per track (MAX)
DISK_RW_GAP DB ? ; Read Write Gap
DISK_DTL DB ?
DISK_FORMT_GAP DB ? ; Format Gap Length
DISK_FILL DB ? ; Format Fill Byte
DISK_HEAD_STTL DB ? ; Head Settle Time (MSec)
DISK_MOTOR_STRT DB ? ; Motor start delay
DISK_PARMS ENDS
ROMStatus equ 1
ROMRead equ 2
ROMWrite equ 3
ROMVerify equ 4
ROMFormat equ 5

76
v4.0/src/BIOS/MSEQU.INC Normal file
View File

@ -0,0 +1,76 @@
%OUT MSEQU.INC...
;==============================================================================
FTOOBIG EQU 80H
FBIG EQU 40H
ROMSTATUS EQU 1
ROMREAD EQU 2
ROMWRITE EQU 3
ROMVERIFY EQU 4
ROMFORMAT EQU 5
VID_SIZE EQU 12
INCLUDE MSBDS.INC ; VARIOUS EQUATES FOR BDS
;AN000; Extended BPB structure.
BPB_TYPE STRUC
SECSIZE DW ?
SECALL DB ?
RESNUM DW ?
FATNUM DB ?
DIRNUM DW ?
SECNUM DW ?
FATID DB ?
FATSIZE DW ?
SLIM DW ?
HLIM DW ?
HIDDEN_L DW ?
HIDDEN_H dw 0 ;J.K.
SECNUM_L dw 0 ;J.K.
SECNUM_H dw 0 ;J.K.
BPB_TYPE ENDS
;;;;;;;;;;;
BOOT_SERIAL_SIZE equ 4 ;J.K.
BOOT_VOLUME_LABEL_SIZE equ 11 ;J.K.
BOOT_SYSTEM_ID_SIZE equ 8 ;J.K.
EXT_BOOT_SIGNATURE equ 41 ;J.K.
RSINIT=0A3H ;RS232 INITIALIZATION
;9600 BAUD:NO PARITY:1 STOP:8 BIT WORD
LF=10 ;LINE FEED
CR=13 ;CARRIAGE RETURN
BACKSP=8 ;BACKSPACE
BRKADR=1BH * 4 ;006C 1BH BREAK VECTOR ADDRESS
TIMADR=1CH * 4 ;0070 1CH TIMER INTERRUPT
DSKADR=1EH * 4 ;ADDRESS OF PTR TO DISK PARAMETERS
SEC9=522H ;ADDRESS OF DISK PARAMETERS
HEADSETTLE=SEC9+9 ; ARR 2.20 ADDRESS OF HEAD SETTLE TIME
NORMSETTLE=15 ; ARR 2.20 NORMAL HEAD SETTLE
SPEEDSETTLE=0 ; ARR 2.20 SPEED UP SETTLE TIME
INITSPOT=534H ; ARR IBM WANTS 4 ZEROS HERE
AKPORT=20H
EOI=20H
CMDLEN = 0 ;LENGTH OF THIS COMMAND
UNIT = 1 ;SUB UNIT SPECIFIER
CMD = 2 ;COMMAND CODE
STATUS = 3 ;STATUS
MEDIA = 13 ;MEDIA DESCRIPTOR
TRANS = 14 ;TRANSFER ADDRESS
COUNT = 18 ;COUNT OF BLOCKS OR CHARACTERS
START = 20 ;FIRST BLOCK TO TRANSFER
EXTRA = 22 ;USUALLY A POINTER TO VOL ID FOR ERROR 15
CHROUT = 29H
MAXERR = 5
LSTDRV = 504H
BOOTBIAS = 200H
NOTBUSYSTATUS = 10000000B ; NOT BUSY
ACKSTATUS = 01000000B ; ACKNOWLEDGE (FOR WHAT?)
NOPAPERSTATUS = 00100000B ; NO MORE PAPER
SELECTEDSTATUS = 00010000B ; THE PRINTER SAID IT WAS SELECTED
IOERRSTATUS = 00001000B ; SOME KINDA ERROR
RESERVED = 00000110B ; NOPS
TIMEOUTSTATUS = 00000001B ; TIME OUT.
ERROR_UNKNOWN_MEDIA = 7 ; FOR USE IN BUILD BPB CALL
PATHGEN = 1

97
v4.0/src/BIOS/MSEXTRN.INC Normal file
View File

@ -0,0 +1,97 @@
; SCCSID = @(#)IBMEXTRN.ASM 1.11 85/11/18
;This is for IBMINIT module.
;=======================================================
;REVISION HISTORY:
;AN000; - NEW Version 4.00. J.K.
;AC000; - Modified Line 4.00. J.K.
;ANxxx; - PTMyyy
;==============================================================================
;AN001; D486 SHARE installation for large media 2/23/88 J.K.
;==============================================================================
EXTRN ORIG13:DWORD,ORIG19:DWORD
EXTRN COM2DEV:WORD,COM1DEV:WORD
EXTRN COM4DEV:WORD,COM3DEV:WORD
EXTRN LPT3DEV:WORD,LPT2DEV:WORD,LPT1DEV:WORD
EXTRN HARDDRV:BYTE,HARDNUM:BYTE,DRVMAX:BYTE,HDSKTAB:WORD
EXTRN DSKDRVS:WORD,HNUM:BYTE,EOT:BYTE,FHAVE96:BYTE
EXTRN REAL13:DWORD,DAYCNT:WORD,CONHEADER:WORD
EXTRN TWOHARD:BYTE,INT_2F_NEXT:DWORD
EXTRN BDSH:WORD,BDSX:WORD,START_BDS:DWORD
EXTRN FHAVEK09:BYTE, NEW_ROM:BYTE
EXTRN SINGLE:BYTE
EXTRN BDSMs:BYTE ;for Mini Disk -J.K. 4/7/86
EXTRN HaveCMOSClock:byte ;set by IBMINIT. Used by IBMCLOCK.ASM
EXTRN BinToBCD:word ;set by IBMINIT. Used by IBMCLOCK.ASM
EXTRN DaycntToDay:word ;set by IBMINIT. Used by IBMCLOCK.ASM
EXTRN OLD13:DWORD
extrn Temp_H:word ;J.K. For 32 bit calculation. IBMDISK
extrn Start_Sec_H:word ;J.K. IBMDISK.
extrn KEYRD_Func:byte ;J.K. For IBMCON. Defined in IBMBDATA.
extrn KEYSTS_Func:byte ;J.K. For IBMCON. Defined in IBMBDATA.
extrn DiskSector:byte ;J.K. IBMBDATA
extrn Bpb_In_Sector:word ;J.K. IBMBDATA
extrn SecPerCLusInSector:Byte ;J.K. IBMBDATA
extrn NumberOfFats:byte ;J.K. IBMBDATA
extrn MediaByte:byte ;J.K. IBMBDATA
extrn Ext_Boot_Sig:Byte ;J.K. IBMBDATA
extrn Boot_Serial_L:Word ;J.K. IBMBDATA
extrn Boot_Serial_H:Word ;J.K. IBMBDATA
extrn Boot_Volume_Label:Byte ;J.K. IBMBDATA
extrn Boot_System_ID:Byte ;J.K. IBMBDATA
extrn Fat_12_ID:Byte ;J.K. IBMDISK
extrn Fat_16_ID:Byte ;J.K. IBMDISK
extrn Vol_No_Name:Byte ;J.K. IBMDISK
extrn MotorStartup:Byte ;J.K. IBMBDATA
extrn DoubleWordMov:Byte ;J.K. IBMDISK
extrn Model_Byte:Byte ;J.K. IBMBIO2
extrn Secondary_Model_Byte:Byte ;J.K. IBMBIO2
IF iTEST
IFNDEF NUMBUF
EXTRN NUMBUF:BYTE,DIGITS:BYTE,FTESTBITS:WORD
ENDIF
ENDIF
EXTRN START$:NEAR,ERROUT:NEAR,BLOCK13:FAR,INT19:FAR
EXTRN INTRET:NEAR,HDRIVE:NEAR,DRIVEX:NEAR,INT13:FAR,CBREAK:NEAR,OUTCHR:NEAR
EXTRN DISKRD:NEAR,MEDIA_PATCH:NEAR,GETBP1_PATCH:NEAR
EXTRN SET_PATCH:NEAR,DISKIO_PATCH:NEAR,DSKERR:NEAR,INIT_PATCH:NEAR
EXTRN TABLE_PATCH:NEAR,EXIT:NEAR,CHANGED_PATCH:NEAR
EXTRN ERRIN:NEAR,GETBP:NEAR,SWPDSK:NEAR
EXTRN OUTCHR:NEAR,WRMSG:NEAR,TIME_TO_TICKS:NEAR
EXTRN INT2F_DISK:NEAR,INSTALL_BDS:NEAR,SETDRIVE:NEAR
extrn Mov_Media_IDs:Near ;J.K.
extrn Clear_IDs:Near ;J.K.
IF iTEST
IFNDEF NUMBUF
EXTRN MSGNUM:NEAR,MSGOUT:NEAR,dumpbytes:near,hex_to_ascii:near
EXTRN outchar:near
ENDIF
ENDIF
SYSINITSEG SEGMENT PUBLIC 'SYSTEM_INIT'
ASSUME CS:SYSINITSEG
EXTRN CURRENT_DOS_LOCATION:WORD
EXTRN FINAL_DOS_LOCATION:WORD
EXTRN DEVICE_LIST:DWORD
EXTRN MEMORY_SIZE:WORD
EXTRN DEFAULT_DRIVE:BYTE
EXTRN BUFFERS:WORD
EXTRN SYSINIT:FAR
extrn Big_Media_Flag:Byte ;AN001;
SYSINITSEG ENDS
ASSUME CS:CODE
; END OF DISK MODULES FOR CONFIGURATION
EXTRN END96TPI:BYTE
EXTRN ENDTWOHARD:BYTE
EXTRN ENDONEHARD:BYTE
EXTRN ENDSWAP:BYTE
EXTRN ENDFLOPPY:BYTE
; IBM FIXED UP AT ROM
EXTRN IBM_DISK_IO:FAR

46
v4.0/src/BIOS/MSGROUP.INC Normal file
View File

@ -0,0 +1,46 @@
EVBOUND = 1 ;THIS VALUE BEING 0 DOES NO BOUNDARY ALLIGNMENT, VALUE 1 ;3.30
; ALIGNS TO EVEN ;3.30
; : : : : : : : : : : : : : : ;3.30
IF EVBOUND ;;IF EVEN (WORD) ALLIGNMENT IS REQUESTED, ;3.30
; : : : : : : : : : : : : : : ;3.30
EVENB MACRO ;3.30
EVEN ;;ADJUST TO EVEN BOUNDARY ;3.30
ENDM ;3.30
;3.30
ODD MACRO ;3.30
;;GENERATE BOUNDARY PADDING TO FORCE ODD OFFSET ;3.30
IF (($-CODE) MOD 2) EQ 0 ;3.30
DB ? ;3.30
ENDIF ;3.30
ENDM ;3.30
;3.30
CODE_SEGMENT MACRO ;3.30
;;ALLIGN THE SEGMENT ON WORD BOUNDARY TO ALLOW FOR EVEN ALLIGNMENT OF DATA;3.30
CODE SEGMENT WORD PUBLIC 'CODE' ;3.30 ;3.30
ENDM ;3.30
;3.30
; : : : : : : : : : : : : : : ;3.30
ELSE ;;SINCE EVEN ALLIGNMENT IS NOT DESIRED, JUST USE BYTE ALLI;3.30 GNMENT
; : : : : : : : : : : : : : : ;3.30
;3.30
EVENB MACRO ;3.30
;;REQUEST FOR WORD ALLIGNMENT DOES NOTHING ;3.30
ENDM ;3.30
;3.30
ODD MACRO ;3.30
;;REQUEST FOR ODD ALLIGNMENT DOES NOTHING ;3.30
ENDM ;3.30
;3.30
CODE_SEGMENT MACRO ;3.30
;;SEGMENT IS ALLIGNED ON BYTE BOUNDARY FOR MINIMUM SIZE OF GENERATION ;3.30
CODE SEGMENT BYTE PUBLIC 'CODE' ;3.30
ENDM ;3.30
;3.30
; : : : : : : : : : : : : : : ;3.30
ENDIF ;3.30
; : : : : : : : : : : : : : : ;3.30
;3.30
CODE_SEGMENT ;3.30
ASSUME CS:CODE ;3.30
;3.30


427
v4.0/src/BIOS/MSHARD.ASM Normal file
View File

@ -0,0 +1,427 @@
;***
; Title: Disk
; C: (C) Copyright 1988 by Microsoft corp.
; Date: 1/11/85
;
; There is a bug in some versions of IBM's AT ROM BIOS.
; Interrupts are not disabled during read operations.
;
; Use: This program should be chained in line with the disk
; interupt 13h, it intercepts read calls to the hard disk
; and handles them appropriately. For other functions it
; passes controll to OLD13, which should contain the
; address of the AT ROM disk routine. The entry point for
; this program is IBM_DISK_IO.
;
.286c ;Use 80286 non-protected mode
BIOSEG = 040h ;Segment for ROM BIOS Data
ROMSEG = 0F000h ;Segment of ROM
BAD_DISK = 01
HF_PORT = 01F0h
HF_REG_PORT = 03F6h
;* Offsets into Fixed disk parameter table
FDP_PRECOMP = 5
FDP_CONTROL = 8
DATA SEGMENT AT BIOSEG ;ROM BIOS data segment
ORG 42h
CMD_BLOCK DB 6 DUP (?)
;* Offsets into CMD_BLOCK for registers
PRE_COMP = 0 ;Write Pre-compensation
SEC_CNT = 1 ;Sector count
SEC_NUM = 2 ;Sector number
CYL_LOW = 3 ;Cylinder number, low part
CYL_HIGH = 4 ;Cylinder number, high part
DRV_HEAD = 5 ;Drive/Head (Bit 7 = ECC mode, Bit 5 = 512 byte sectors,
; Bit 4 = drive number, Bits 3-0 have head number)
CMD_REG = 6 ;Command register
ORG 074h
DISK_STATUS1 DB ?
HF_NUM DB ?
CONTROL_BYTE DB ?
DATA ENDS
;*** Define where the ROM routines are actually located
ROM SEGMENT AT ROMSEG
ORG 02E1Eh
ROMCOMMAND PROC FAR
ROMCOMMAND ENDP
ORG 02E7Fh
ROMWAIT PROC FAR
ROMWAIT ENDP
ORG 02EE2h
ROMWAIT_DRQ PROC FAR
ROMWAIT_DRQ ENDP
ORG 02EF8h
ROMCHECK_STATUS PROC FAR
ROMCHECK_STATUS ENDP
ORG 02F69h
ROMCHECK_DMA PROC FAR
ROMCHECK_DMA ENDP
ORG 02F8Eh
ROMGET_VEC PROC FAR
ROMGET_VEC ENDP
ORG 0FF65h
ROMFRET PROC FAR ;Far return at F000:FF65 in AT ROM.
ROMFRET ENDP
ROM ENDS
CODE SEGMENT BYTE PUBLIC 'code'
EXTRN OLD13:DWORD ;Link to AT bios int 13h
PUBLIC IBM_DISK_IO
ASSUME CS:CODE
ASSUME DS:DATA
;*** IBM_DISK_IO - main routine, fixes AT ROM bug
;
; ENTRY: (AH) = function, 02 or 0A for read.
; (DL) = drive number (80h or 81h).
; (DH) = head number.
; (CH) = cylinder number.
; (CL) = Sector number (high 2 bits has cylinder number).
; (AL) = number of sectors.
; (ES:BX) = address of read buffer.
; For more on register contents see ROM BIOS listing.
; Stack set up for return by an IRET.
;
; EXIT: (AH) = status of current operation.
; (CY) = 1 IF failed, 0 if successful.
; For other register contents see ROM BIOS listing.
;
; USES:
;
;
; WARNING: Uses OLD13 vector for non-read calls.
; Does direct calls to the AT ROM.
; Does segment arithmatic.
;
; EFFECTS: Performs DISK I/O operation.
;
IBM_DISK_IO PROC FAR
CMP DL, 80h
JB ATD1 ;Pass through floppy disk calls.
CMP AH, 02
JE ATD2 ;Intercept call 02 (read sectors).
CMP AH, 0Ah
JE ATD2 ;and call 0Ah (read long).
ATD1:
JMP OLD13 ;Use ROM INT 13h handler.
ATD2:
PUSH BX
PUSH CX
PUSH DX
PUSH DI
PUSH DS
PUSH ES
PUSH AX
MOV AX,BIOSEG ;Establish BIOS segment addressing.
MOV DS,AX
MOV DISK_STATUS1, 0 ;Initially no error code.
AND DL, 07fh ;Mask to hard disk number
CMP DL, HF_NUM
JB ATD3 ;Disk number in range
MOV DISK_STATUS1, BAD_DISK
JMP SHORT ATD4 ;Disk number out of range error, return
ATD3:
PUSH BX
MOV AX, ES ;Make ES:BX to Seg:000x form.
SHR BX, 4
ADD AX, BX
MOV ES, AX
POP BX
AND BX,000Fh
PUSH CS
CALL CHECK_DMA
JC ATD4 ;Abort if DMA across segment boundary
POP AX ;Restore AX register for SETCMD
PUSH AX
CALL SETCMD ;Set up command block for disk op
MOV DX, HF_REG_PORT
OUT DX, AL ;Write out command modifier
CALL DOCMD ;Carry out command
ATD4:
;; Old code - Carry cleared after set by logical or opearation
;; POP AX
;; MOV AH,DISK_STATUS1 ;On return AH has error code
;; STC
;; OR AH,AH
;; JNZ ATD5 ;Carry set if error
;; CLC
;;---------------------------------------------------
;; New Code - Let Logical or clear carry and then set carry if ah!=0
;; And save a couple bytes while were at it.
POP AX
MOV AH,DISK_STATUS1 ;On return AH has error code
OR AH,AH
JZ ATD5 ;Carry set if error
STC
ATD5:
POP ES
POP DS
POP DI
POP DX
POP CX
POP BX
RET 2 ;Far return, dropping flags
IBM_DISK_IO ENDP
;*** SETCMD - Set up CMD_BLOCK for the disk operation
;
; ENTRY: (DS) = BIOS Data segment.
; (ES:BX) in seg:000x form.
; Other registers as in INT 13h call
;
; EXIT: CMD_BLOCK set up for disk read call.
; CONTROL_BYTE set up for disk operation.
; (AL) = Control byte modifier
;
;
; Sets the fields of CMD_BLOCK using the register contents
; and the contents of the disk parameter block for the given drive.
;
; WARNING: (AX) destroyed.
; Does direct calls to the AT ROM.
;
SETCMD PROC NEAR
MOV CMD_BLOCK[SEC_CNT], AL
MOV CMD_BLOCK[CMD_REG], 020h ;Assume function 02
CMP AH, 2
JE SETC1 ;CMD_REG = 20h if function 02 (read)
MOV CMD_BLOCK[CMD_REG], 022h ;CMD_REG = 22h if function 0A (" long)
SETC1: ;No longer need value in AX
MOV AL, CL
AND AL, 03fh ;Mask to sector number
MOV CMD_BLOCK[SEC_NUM], AL
MOV CMD_BLOCK[CYL_LOW], CH
MOV AL, CL
SHR AL, 6 ;Get two high bits of cylender number
MOV CMD_BLOCK[CYL_HIGH], AL
MOV AX, DX
SHL AL, 4 ;Drive number
AND AH, 0Fh
OR AL, AH ;Head number
OR AL, 0A0h ;Set ECC and 512 bytes per sector
MOV CMD_BLOCK[DRV_HEAD], AL
PUSH ES ;GET_VEC destroys ES:BX
PUSH BX
PUSH CS
CALL GET_VEC
MOV AX, ES:FDP_PRECOMP[BX] ;Write pre-comp from disk parameters
SHR AX, 2
MOV CMD_BLOCK[PRE_COMP],AL ;Only use low part
MOV AL, ES:FDP_CONTROL[BX] ;Control byte modifier
POP BX
POP ES
MOV AH, CONTROL_BYTE
AND AH, 0C0h ;Keep disable retry bits
OR AH, AL
MOV CONTROL_BYTE, AH
RET
SETCMD ENDP
;*** DOCMD - Carry out READ operation to AT hard disk
;
; ENTRY: (ES:BX) = address for read in data.
; CMD_BLOCK set up for disk read.
;
; EXIT: Buffer at (ES:BX) contains data read.
; DISK_STATUS1 set to error code (0 if success).
;
;
;
; WARNING: (AX), (BL), (CX), (DX), (DI) destroyed.
; No check is made for DMA boundary overrun.
;
; EFFECTS: Programs disk controller.
; Performs disk input.
;
DOCMD PROC NEAR
MOV DI, BX ;(ES:DI) = data buffer addr.
PUSH CS
CALL COMMAND
JNZ DOC3
DOC1:
PUSH CS
CALL WAITT ;Wait for controller to complete read
JNZ DOC3
MOV CX, 100h ;256 words per sector
MOV DX, HF_PORT
CLD ;String op goes up
CLI ;Disable interrupts (BUG WAS FORGETTING THIS)
REPZ INSW ;Read in sector
STI
TEST CMD_BLOCK[CMD_REG], 02
JZ DOC2 ;No ECC bytes to read.
PUSH CS
CALL WAIT_DRQ
JC DOC3
MOV CX, 4 ;4 bytes of ECC
MOV DX, HF_PORT
CLI
REPZ INSB ;Read in ECC
STI
DOC2:
PUSH CS
CALL CHECK_STATUS
JNZ DOC3 ;Operation failed
DEC CMD_BLOCK[SEC_CNT]
JNZ DOC1 ;Loop while more sectors to read
DOC3:
RET
DOCMD ENDP
;*** GET_VEC - Get pointer to hard disk parameters.
;
; ENTRY: (DL) = Low bit has hard disk number (0 or 1).
;
; EXIT: (ES:BX) = address of disk parameters table.
;
; USES: AX for segment computation.
;
; Loads ES:BX from interrupt table in low memory, vector 46h (disk 0)
; or 70h (disk 1).
;
; WARNING: (AX) destroyed.
; This does a direct call to the AT ROM.
;
GET_VEC PROC NEAR
PUSH OFFSET ROMFRET
JMP ROMGET_VEC
GET_VEC ENDP
;*** COMMAND - Send contents of CMD_BLOCK to disk controller.
;
; ENTRY: Control_byte
; CMD_BLOCK - set up with values for hard disk controller.
;
; EXIT: DISK_STATUS1 = Error code.
; NZ if error, ZR for no error.
;
;
; WARNING: (AX), (CX), (DX) destroyed.
; Does a direct call to the AT ROM.
;
; EFFECTS: Programs disk controller.
;
COMMAND PROC NEAR
PUSH OFFSET ROMFRET
JMP ROMCOMMAND
COMMAND ENDP
;*** WAITT - Wait for disk interrupt
;
; ENTRY: Nothing.
;
; EXIT: DISK_STATUS1 = Error code.
; NZ if error, ZR if no error.
;
;
; WARNING: (AX), (BL), (CX) destroyed.
; Does a direct call to the AT ROM.
;
; EFFECTS: Calls int 15h, function 9000h.
;
WAITT PROC NEAR
PUSH OFFSET ROMFRET
JMP ROMWAIT
WAITT ENDP
;*** WAIT_DRQ - Wait for data request.
;
; ENTRY: Nothing.
;
; EXIT: DISK_STATUS1 = Error code.
; CY if error, NC if no error.
;
;
; WARNING: (AL), (CX), (DX) destroyed.
; Does a direct call to the AT ROM.
;
WAIT_DRQ PROC NEAR
PUSH OFFSET ROMFRET
JMP ROMWAIT_DRQ
WAIT_DRQ ENDP
;*** CHECK_STATUS - Check hard disk status.
;
; ENTRY: Nothing.
;
; EXIT: DISK_STATUS1 = Error code.
; NZ if error, ZR if no error.
;
;
; WARNING: (AX), (CX), (DX) destroyed.
; Does a direct call to the AT ROM.
;
CHECK_STATUS PROC NEAR
PUSH OFFSET ROMFRET
JMP ROMCHECK_STATUS
CHECK_STATUS ENDP
;*** CHECK_DMA - check for DMA overrun 64k segment.
;
; ENTRY: (ES:BX) = addr. of memory buffer in seg:000x form.
; CMD_BLOCK set up for operation.
;
; EXIT: DISK_STATUS1 - Error code.
; CY if error, NC if no error.
;
;
; WARNING: Does a direct call to the AT ROM.
;
CHECK_DMA PROC NEAR
PUSH OFFSET ROMFRET
JMP ROMCHECK_DMA
CHECK_DMA ENDP
CODE ENDS
END

2819
v4.0/src/BIOS/MSINIT.ASM Normal file

File diff suppressed because it is too large Load Diff

1362
v4.0/src/BIOS/MSIOCTL.INC Normal file

File diff suppressed because it is too large Load Diff

1090
v4.0/src/BIOS/MSLOAD.ASM Normal file

File diff suppressed because it is too large Load Diff

7
v4.0/src/BIOS/MSLOAD.INC Normal file
View File

@ -0,0 +1,7 @@
;MSLOAD.INC
End_Of_File equ 0FFh
FAT12_Bit equ 01h
FAT16_Bit equ 04h
ROM_TELETYPE equ 14 ;INT 10h, Teletype function
NUM_DIR_PER_SECTOR equ 16 ; number of directory entries per sector

270
v4.0/src/BIOS/MSLPT.ASM Normal file
View File

@ -0,0 +1,270 @@
PAGE ,132 ;
TITLE MSLPT - BIOS
%OUT ...MSLPT.ASM
;==============================================================================
;REVISION HISTORY:
;AN000 - New for DOS Version 4.00 - J.K.
;AC000 - Changed for DOS Version 4.00 - J.K.
;AN00x - PTM number for DOS Version 4.00 - J.K.
;==============================================================================
;AN001 - P156 KBMLPT device driver's retry logic. 8/18/87 J.K.
;==============================================================================
itest=0
INCLUDE MSGROUP.INC ;DEFINE CODE SEGMENT
INCLUDE MSEQU.INC
INCLUDE MSMACRO.INC
INCLUDE DEVSYM.INC
INCLUDE IOCTL.INC
EXTRN BUS$EXIT:NEAR ;MSBIO1
EXTRN ERR$CNT:NEAR ;MSBIO1
EXTRN CMDERR:NEAR ;MSBIO1
EXTRN GETDX:NEAR ;MSBIO1
EXTRN EXIT:NEAR ;MSBIO1
EXTRN ERR$EXIT:NEAR ;MSBIO1
;DATA
EXTRN PTRSAV:DWORD ;MSBIO1
EXTRN TIMDEV:WORD ;MSCLOCK
EXTRN LPT2DEV:WORD ;MSBIO2
EXTRN WAIT_COUNT:WORD ;MSDATA
EXTRN PRINTDEV:BYTE ;MSDATA
; IBM ROM STATUS BITS (I DON'T TRUST THEM, NEITHER SHOULD YOU)
NOTBUSYSTATUS = 10000000B ; NOT BUSY
ACKSTATUS = 01000000B ; ACKNOWLEDGE (FOR WHAT?)
NOPAPERSTATUS = 00100000B ; NO MORE PAPER
SELECTEDSTATUS = 00010000B ; THE PRINTER SAID IT WAS SELECTED
IOERRSTATUS = 00001000B ; SOME KINDA ERROR
RESERVED = 00000110B ; NOPS
TIMEOUTSTATUS = 00000001B ; TIME OUT.
; WARNING!!! THE IBM ROM DOES NOT RETURN JUST ONE BIT. IT RETURNS A
; WHOLE SLEW OF BITS, ONLY ONE OF WHICH IS CORRECT.
;----------------------------------------------------------
;J.K. AN001; PRN$WRIT will retry only if error code is TIMEOUT.
; WRITE TO PRINTER DEVICE
; CX HAS COUNT OF BYTES
; ES:DI POINT TO DESTINATION
; AUXNUM HAS PRINTER NUMBER
PUBLIC PRN$WRIT
PRN$WRIT PROC NEAR
ASSUME DS:CODE ; SET BY PRINTER DEVICE DRIVER ENTRY
jcxz Prn$Done ;No char to output
Prn$Loop:
mov bx, 2 ;Initialize retry count
Prn$Out:
;SB34LPT000****************************************************************
;SB Print the character at ES:[DI]
;SB Call the function PrnOP to do this
;SB The character to be printed goes in AL and the function code
;SB for 'Output character' goes in AH
;SB Check for error in printing.
;SB If there is no error go to print the next character.
;SB If there is an error indicated see if it is due to TIMEOUT. If the
;SB error is not TIMEOUT then we can do nothing about it. Just go to
;SB print the next character. If it is due to timeout we can execute
;SB the code to retry the print which follows this piece of code
;SB LOCS: 6
mov al,es:[di] ; assume AX disposible since enter
xor ah,ah ; via int 21h
call PrnOp ; print to printer
jz Prn$Con ; no error - continue
test ah,TIMEOUTSTATUS
jz Prn$Con ; NOT time out - continue
;SB34LPT000****************************************************************
dec bx ;Retry until count is exhausted.
jnz Prn$Out ;Retry it.
jmp short Pmessg ;Return with error.
;
; next character
;
Prn$Con:
inc di ;point to next char and continue
loop Prn$Loop
Prn$Done:
jmp Exit
Pmessg:
jmp Err$Cnt
PRN$WRIT endp
; JCXZ EXVEC3 ; NO CHARS TO OUTPUT..
;PRN$LOOP:
; MOV BX,2 ; INITIALIZE RETRY FLAG
;PRN$OUT:
; MOV AL,ES:[DI] ; GET CHAR INTO AL
; INC DI ; POINT TO NEXT CHAR
; XOR AH,AH ; AH=0 => OUTPUT CHAR IN DL
; CALL PRNOP ; TO INDICATE PRINT CHAR IN AL
; JNZ PRRETRY
; LOOP PRN$LOOP
;EXVEC3:
; JMP EXIT
;PRRETRY:
; DEC DI ; UNDO THE INC ABOVE...
; DEC BX
; JNZ PRN$OUT
;PMESSG:
; JMP ERR$CNT ;RETURN WITH THE ERROR
;PRN$WRIT ENDP
;--------------------------------------------------------
; PRINTER STATUS ROUTINE
PUBLIC PRN$STAT
PRN$STAT PROC NEAR
ASSUME DS:CODE ; SET BY PRINTER DEVICE DRIVER ENTRY
CALL PRNSTAT ;DEVICE IN DX
JNZ PMESSG ; OTHER ERRORS WERE FOUND
;J.K. The next three lines are commented out, since it is a dead code.
; MOV AL,9 ; AGAIN, ASSUME OUT OF PAPER...
; TEST AH,NOPAPERSTATUS
; JNZ PMESSG
TEST AH,NOTBUSYSTATUS
jnz Prn$Done ;No error. Exit
JMP BUS$EXIT
PRN$STAT ENDP
; TAKE THE APPROPRIATE PRINTER AND DO THE OPERATION. TRIAGE THE STATUS
; RETURNED IN AH INTO SOME MEANINGFUL ERROR.
PRNSTAT PROC NEAR
;SB33037**********************************************************************
mov AH, 2 ; set command for get status ;SB ;3.30*
PRNOP: ;SB ;3.30*
call GETDX ; determine which printer ;SB ;3.30*
int 17h ; call ROM-BIOS printer routine ;SB;3.30*
;SB33037**********************************************************************
; EXAMINE THE STATUS BITS TO SEE IF AN ERROR OCCURRED. UNFORTUNATELY, SEVERAL
; OF THE BITS ARE SET SO WE HAVE TO PICK AND CHOOSE. WE MUST BE EXTREMELY
; CAREFUL ABOUT BREAKING BASIC.
TEST AH,IOERRSTATUS ; I/O ERROR?
JZ CHECKNOTREADY ; NO, TRY NOT READY
; AT THIS POINT, WE KNOW WE HAVE AN ERROR. THE CONVERSE IS NOT TRUE.
MOV AL,9 ; FIRST, ASSUME OUT OF PAPER
TEST AH,NOPAPERSTATUS ; OUT OF PAPER SET?
JNZ RET1 ; YES, ERROR IS SET
INC AL ; INDICATE I/O ERROR
RET1:
; WE HAVE TRIAGED NOW FOR OUT OF PAPER AND IO ERR (IGNORING TIME-OUT)
RET ; RETURN WITH ERROR
; THE BITS SAID NO ERROR. UNFORTUNATELY, THERE MAY BE OTHER THINGS AT WORK
; HERE.
CHECKNOTREADY:
MOV AL,2 ; ASSUME NOT-READY
TEST AH,TIMEOUTSTATUS ; IS TIME-OUT SET?
; IF NZ THEN ERROR, ELSE OK???
PRNOP2:
RET
PRNSTAT ENDP
; OUTPUT UNTIL BUSY. THIS ENTRY POINT IS USED EXCLUSIVELY BY THE PRINT
; SPOOLERS. UNDER NO CURCUMSTANCES SHOULD THE DEVICE DRIVER BLOCK WAITING FOR
; THE DEVICE TO BECOME READY.
; INPUTS: CX HAS COUNT OF BYTES TO OUTPUT.
; ES:DI POINTS TO SOURCE BUFFER
; OUTPUTS: SET THE NUMBER OF BYTES TRANSFERRED APPROPRIATELY
PUBLIC PRN$TILBUSY
PRN$TILBUSY PROC NEAR
ASSUME DS:CODE ; SET BY PRINTER DEVICE DRIVER ENTRY
PUSH DS
PUSH ES
POP DS ; NOW ES AND DS BOTH POINT TO SOURCE BUFFER
ASSUME DS:NOTHING
MOV SI,DI ; EVERYTHING IS SET FOR LODSB
PRN$TILBLOOP:
PUSH CX
PUSH BX
XOR BX,BX
MOV BL,CS:[PRINTDEV]
SHL BX,1
MOV CX,CS:WAIT_COUNT[BX] ; WAIT COUNT TIMES TO COME READY
POP BX
PRN$GETSTAT:
CALL PRNSTAT ; GET STATUS
JNZ PRN$BPERR ; ERROR
TEST AH,10000000B ; READY YET?
LOOPZ PRN$GETSTAT ; NO, GO FOR MORE
POP CX ; GET ORIGINAL COUNT
JZ PRN$BERR ; STILL NOT READY => DONE
LODSB
XOR AH,AH
CALL PRNOP
JNZ PRN$BERR ; ERROR
LOOP PRN$TILBLOOP ; GO FOR MORE
PRN$B:
POP DS
LDS BX,CS:[PTRSAV]
ASSUME DS:NOTHING
SUB WORD PTR [BX].COUNT,CX ;# OF SUCCESSFUL I/O'S
JMP EXIT
PRN$TILBUSY ENDP
PRN$BPERR PROC NEAR
ASSUME DS:CODE
POP CX
PRN$BERR:
POP DS
LDS BX,CS:[PTRSAV]
ASSUME DS:NOTHING
SUB WORD PTR [BX].COUNT,CX ;# OF SUCCESSFUL I/O'S
JMP ERR$EXIT
PRN$BPERR ENDP
;
; MANIPULATES THE VALUE IN WAIT_COUNT DEPENDING ON THE VALUE PASSED IN THE
; GENERIC IOCTL PACKET.
; IT EITHER SETS OR RETURNS THE CURRENT VALUE FOR THE RETRY COUNT FOR THE
; DEVICE.
;
PUBLIC PRN$GENIOCTL
PRN$GENIOCTL PROC NEAR
ASSUME DS:CODE ; SET BY PRINTER DEVICE DRIVER ENTRY
LES DI,[PTRSAV]
CMP ES:[DI].MAJORFUNCTION,IOC_PC
JE PRNFUNC_OK
PRNFUNCERR:
JMP CMDERR
PRNFUNC_OK:
MOV AL,ES:[DI].MINORFUNCTION
LES DI,ES:[DI].GENERICIOCTL_PACKET
XOR BX,BX
MOV BL,[PRINTDEV] ; GET INDEX INTO RETRY COUNTS
SHL BX,1
MOV CX,WAIT_COUNT[BX] ; PULL OUT RETRY COUNT FOR DEVICE
CMP AL,GET_RETRY_COUNT
JZ PRNGETCOUNT
CMP AL,SET_RETRY_COUNT
JNZ PRNFUNCERR
MOV CX,ES:[DI].RC_COUNT
PRNGETCOUNT:
MOV WAIT_COUNT[BX],CX ; PLACE "NEW" RETRY COUNT
MOV ES:[DI].RC_COUNT,CX ; RETURN CURRENT RETRY COUNT
JMP EXIT
PRN$GENIOCTL ENDP
CODE ENDS
END

192
v4.0/src/BIOS/MSMACRO.INC Normal file
View File

@ -0,0 +1,192 @@
;
; This file contains three macros used in debugging the system. If the
; variable "itest" (in msbio.asm) is nonzero code is included in the
; modules to print debugging messages. The level of debugging is controlled
; by the value of the variable fTestBits in msbio.asm. Specific bits in
; the variable determine which messages to print. The equ's below tell
; which bits control which funcitons. For example the fifth bit
; cooresponds to disk activity (see fTestDisk equ below).
;
; The macros in the file are:
;
; message Prints an ascii string on the screen.
; Example usage:
;
; message fTestDisk, <"Start Disk Write", CR, LF>
; message fTestINIT, <"Begin BDS initialization">
;
;
; MNUM Print the value in a register or memory location on
; the screen. Value is displayed in hex.
; Usage:
; MNUM bitpattern, valueLocation
;
; valueLocation is typically a regester:
;
; mnum fTestCom, AX
; mnum fTestDisk, DX
;
; ValueLocation can also be a memory location:
;
; mnum fTestINIT, Final_Dos_Location
;
; If no valueLocation is given the macro defaults to
; the BX register.
;
; ZWAIT Stops the program until any key is pressed.
;
;
; The three macros preserve all register values. If "test" is zero
; defined during assembly then the marco produce no code.
;
IF iTEST ;3.30
IFNDEF MSGOUT ;3.30
EXTRN MSGOUT:NEAR,MSGNUM:NEAR ;3.30
ENDIF ;3.30
IFNDEF NUMBUF ;3.30
EXTRN NUMBUF:BYTE,DIGITS:BYTE,FTESTBITS:WORD ;3.30
ENDIF ;3.30
IFNDEF DUMPBYTES ;3.30
EXTRN DUMPBYTES:NEAR,OUTCHAR:NEAR,HEX_TO_ASCII:NEAR ;3.30
ENDIF ;3.30
fTestALL equ 1111111111111111b ; watch everything
fTestHARD equ 0000000000000001b ; watch hard disk initialization
fTest96 equ 0000000000000010b ; watch 96 tpi activity
FTEST13 EQU 0000000000000100B ; WATCH INT 13 ACTIVITY ;3.30
FTESTCOM EQU 0000000000001000B ; WATCH PACKET ACTIVITY ;3.30
FTESTINIT EQU 0000000000010000B ; WATCH INITIALIZATION MESSAGES ;3.30
FTESTDISK EQU 0000000000100000B ; WATCH DISK DEVICE DRIVER CALLS ;3.30
FTESTCON EQU 0000000001000000B ; WATCH SYSTEM WAIT ACTIVITY IN CO;3.30 NSOLE
FtestClock equ 0000000010000000b ; wathc clock device 5/2/86 ;3.30
;
; message macro -- see above for description
;
MESSAGE MACRO Bits,msg
LOCAL A,B ;3.30
jmp SHORT b
a: db msg,0
b: push SI
push AX
mov AX,Bits
mov SI,OFFSET a
call MSGOUT
pop AX
pop SI
endm
;
; mnum macro -- see above for description
;
MNum MACRO Bits,num
push AX
ifb <num>
mov AX,Bits
call MSGNUM
else
push BX
mov BX,num
mov AX,Bits
call MSGNUM
pop BX
endif
pop AX
endm
;
; zwait macro -- see above for description
;
ZWAIT MACRO
Message fTestALL,<"? ">
CALL ZWAITrtn
ENDM
ZWAITrtn:
pushf ; save the flags
push AX ; preserve AX
xor AH, AH ; set command to get character ;3.30*
int 16h ; call rom keyboard routine ;3.30*
pop AX ; restore AX
popf ; restore the flags
ret
;Dump_byte dumps the memory contents in hex. ;3.30
;DUMPOFFLABEL should be a label or a variable defined in DUMPSEG. ;3.30
DUMP_BYTE MACRO DUMPSEG, DUMPOFFLABEL, BYTELENGTH ;3.30
push es ;3.30
PUSH DS ;3.30
PUSH SI ;3.30
PUSH CX ;3.30
;3.30
MOV CX, DUMPSEG ;3.30
MOV DS, CX ;3.30
MOV SI, OFFSET DUMPOFFLABEL ;3.30
MOV CX, BYTELENGTH ;3.30
call dumpbytes ;3.30
;3.30
POP CX ;3.30
POP SI ;3.30
POP DS ;3.30
pop es ;3.30
ENDM ;3.30
;3.30
;Dump_Byte_Reg dumps the memory contents in hex. - 4/9/86 ;3.30
;DUMPOFFREG should be a register contains the offset value in DUMPSEG. ;3.30
DUMP_BYTE_REG MACRO DUMPSEG, DUMPOFFREG, BYTELENGTH ;3.30
push es ;3.30
PUSH DS ;3.30
PUSH SI ;3.30
PUSH CX ;3.30
;3.30
MOV CX, DUMPSEG ;3.30
MOV DS, CX ;3.30
MOV SI, DUMPOFFREG ;3.30
MOV CX, BYTELENGTH ;3.30
call dumpbytes ;3.30
;3.30
POP CX ;3.30
POP SI ;3.30
POP DS ;3.30
pop es ;3.30
ENDM ;3.30
else
; if test is not defined then make macro into null statements
Message macro
ENDM
MNUM macro
ENDM
ZWAIT macro
ENDM
DUMP_BYTE MACRO ;3.30
ENDM ;3.30
DUMP_BYTE_REG MACRO ;3.30
ENDM ;3.30
ENDIF ;3.30
;3.30
PATHSTART MACRO INDEX,ABBR ;3.30
IFDEF PATHGEN ;3.30
PUBLIC ABBR&INDEX&S,ABBR&INDEX&E ;3.30
ABBR&INDEX&S LABEL BYTE ;3.30
ENDIF ;3.30
ENDM ;3.30
;3.30
PATHEND MACRO INDEX,ABBR ;3.30
IFDEF PATHGEN ;3.30
ABBR&INDEX&E LABEL BYTE ;3.30
ENDIF ;3.30
ENDM ;3.30

306
v4.0/src/BIOS/MSSTACK.INC Normal file
View File

@ -0,0 +1,306 @@
; MSStack.inc
;
; Interrupt level 2, 3, 4, 5, 6, 7,(10, 11, 12, 14, 15 - AT level)
; should follow the standard Interrupt Sharing Scheme which has
; a standard header structure.
; Fyi, the following shows the relations between
; the interrupt vector and interrupt level.
; VEC(Hex) 2 8 9 A B C D E 70 72 73 74 76 77
; LVL(Deci) 9 0 1 2 3 4 5 6 8 10 11 12 14 15
; MSSTACK module modifies the following interrupt vectors
; to meet the standard Interrupt Sharing standard;
; A, B, C, D, E, 72, 73, 74, 76, 77.
; Also, for interrupt level 7 and 15, the FirstFlag in a standard header
; should be initialized to indicat whether this interrupt handler is
; the first (= 80h) or not. The FirstFlag entry of INT77h's
; program header is initialized in STKINIT.INC module.
; FirstFlag is only meaningful for interrupt level 7 and 15.
;
; User specifies the number of stack elements - default = 9
; minimum = 8
; maximum = 64
;
; Intercepts Asynchronous Hardware Interrupts only
;
; Picks a stack from pool of stacks and switches to it
;
; Calls the previously saved interrupt vector after pushing flags
;
; On return, returns the stack to the stack pool
;
; This is a modification of STACKS:
; 1. To fix a bug which was causing the program to take up too much space.
; 2. To dispense stack space from hi-mem first rather than low-mem first.
; . Clobbers the stack that got too big instead of innocent stack
; . Allows system to work if the only stack that got too big was the most
; deeply nested one
; 3. Disables NMI interrupts while setting the NMI vector.
; 4. Does not intercept any interupts on a PCjr.
; 5. Double checks that a nested interrupt didn't get the same stack.
; 6. Intercepts Ints 70, 72-77 for PC-ATs and other future products
;The following variables are for MSSTACK.inc
EVEN
dw 0 ; SPARE FIELD BUT LEAVE THESE IN ORDER
StackCount dw 0
StackAt dw 0
StackSize dw 0
Stacks dw 0
dw 0
FirstEntry dw Stacks
LastEntry dw Stacks+(DefaultCount*EntrySize)-EntrySize
NextEntry dw Stacks+(DefaultCount*EntrySize)-EntrySize
;End of variables defined for MSSTACK.
;*******************************************************************
;Macro Interrupt handler for the ordinary interrupt vectors and
;the shared interrupt vectors.
;*****************************
Stack_Main MACRO AA
ASSUME DS:NOTHING
ASSUME ES:NOTHING
ASSUME SS:NOTHING
PUBLIC Int&AA
PUBLIC Old&AA
;-----------------------------
ife IntSharingFlag ;if not IntSharingFlag
;-----------------------------
Old&AA DD 0
Int&AA PROC FAR
;-----------------------------
else ;for shared interrupt. A Header exists.
PUBLIC FirstFlag&AA
Int&AA PROC FAR
jmp short Entry_Int&AA&_Stk
Old&AA dd 0 ;Forward pointer
dw 424Bh ;compatible signature for Int. Sharing
FirstFlag&AA db 0 ;the firstly hooked.
jmp short Intret_&AA ;Reset routine. We don't care this.
db 7 dup (0) ;Reserved for future.
Entry_Int&AA&_Stk:
;-----------------------------
endif
;-----------------------------
;
; Keyboard interrupt must have a three byte jump, a NOP and a zero byte
; as its first instruction for compatibility reasons
ifidn <&aa>,<09>
jmp Keyboard_lbl
nop
db 0
Keyboard_lbl label near
endif
; This patches INTERRUPT 75h to be "unhooked". We do this Wierdness,
; rather than never hooking INT 75h, to maintain maximum compat. with IBMs
; post production patch.
push ax
ifidn <&aa>,<02>
; *********************************************************************
;
; This is special support for the PC Convertible / NMI handler
;
; On the PC Convertible, there is a situation where an NMI can be
; caused by using the "OUT" instructions to certain ports. When this
; occurs, the PC Convertible hardware *GUARANTEES* that **NOTHING**
; can stop the NMI or interfere with getting to the NMI handler. This
; includes other type of interrupts (hardware and software), and
; also includes other type of NMI's. When any NMI has occured,
; no other interrtupt (hardware, software or NMI) can occur until
; the software takes specific steps to allow further interrupting.
;
; For PC Convertible, the situation where the NMI is generated by the
; "OUT" to a control port requires "fixing-up" and re-attempting. In
; otherwords, it is actually a "restartable exception". In this
; case, the software handler must be able to get to the stack in
; order to figure out what instruction caused the problem, where
; it was "OUT"ing to and what value it was "OUT"ing. Therefore,
; we will not switch stacks in this situation. This situation is
; detected by interrogating port 62h, and checking for a bit value
; of 80h. If set, *****DO NOT SWITCH STACKS*****.
;
; *********************************************************************
push es
mov ax,0f000h
mov es,ax
cmp byte ptr es:[0fffeh],mdl_convert ;check if convertible
pop es
jne Normal&aa
in al,62h
test al,80h
jz Normal&aa
Special&aa:
pop ax
jmp dword ptr Old&aa
Normal&aa:
; *********************************************************************
endif
push bp
push es
mov es, cs:[STACKS+2] ; Get segment of stacks
mov bp,NextEntry ; get most likely candidate
mov al,Allocated
xchg AllocByte,al ; grab the entry
cmp al,Free ; still avail?
jne NotFree&aa
sub NextEntry,EntrySize ; set for next interrupt
Found&aa:
mov SavedSP,sp ; save sp value
mov SavedSS,ss ; save ss also
; mov IntLevel,aa&h ; save the int level
mov ax,bp ; temp save of table offset
mov bp,NewSP ; get new SP value
cmp es:[bp],ax ; check for offset into table
jne FoundBad&aa
mov ax,es ; point ss,sp to the new stack
mov ss,ax
mov sp,bp
pushf ; go execute the real interrupt handler
call dword ptr old&aa ; which will iret back to here
mov bp,sp ; retrieve the table offset for us
mov bp,es:[bp] ; but leave it on the stack
mov ss,SavedSS ; get old stack back
mov sp,SavedSP
; cmp AllocByte,Allocated ; If an error occured,
; jne NewError&aa ; do not free us
mov AllocByte,Free ; free the entry
mov NextEntry,bp ; setup to use next time
NewError&aa:
pop es
pop bp ; saved on entry
pop ax ; saved on entry
INTRET_&AA: ;3.30
iret ; done with this interrupt
NotFree&aa:
cmp al,Allocated ; error flag
je findnext&aa ; no, continue
xchg AllocByte,al ; yes, restore error value
FindNext&aa:
call LongPath
jmp Found&aa
FoundBad&aa:
cmp bp,FirstEntry
jc findnext&aa
mov bp,ax ; flag this entry
mov AllocByte,Clobbered
; add bp,EntrySize ; and previous entry
; mov AllocByte,Overflowed
; sub bp,EntrySize
jmp findnext&aa ; keep looking
int&aa endp
endm
;***************************** ;3.30
;End of Macro definition ;3.30
;******************************************************************** ;3.30
; THESE ARE THE INDIVIDUAL INTERRUPT HANDLERS ;3.30
;3.30
IRP A,<02,08,09,70> ;3.30
IntSharingFlag=0 ;3.30
Stack_Main &A ;3.30
ENDM ;3.30
;3.30
IRP A,<0A,0B,0C,0D,0E,72,73,74,76,77> ;3.30
IntSharingFlag=1 ;3.30
Stack_Main &A ;3.30
ENDM ;3.30
;3.30
;******************************************************************** ;3.30
;Common routines ;3.30
longpath:
mov bp,LastEntry ; start with last entry in table
LPLOOPP: ;3.30
cmp AllocByte,Free ; is entry free?
jne inuse ; no, try next one
mov al,Allocated
xchg AllocByte,al ; allocate entry
cmp al,Free ; is it still free?
je found ; yes, go use it
cmp al,Allocated ; is it other than Allocated or Free?
je inuse ; no, check the next one
mov AllocByte,al ; yes, put back the error state
inuse:
cmp bp,FirstEntry
je Fatal
sub bp,EntrySize
JMP LPLOOPP ;3.30
found:
ret
page
fatal proc near
push ds ;3.30
mov ax, 0f000h ;loook at the model byte ;3.30
mov ds, ax ;3.30
cmp ds:byte ptr [0fffeh], mdl_convert ;convertible? ;3.30
pop ds ;3.30
jne Skip_NMIS ;3.30
;3.30
mov al,07h ; disable PC Convertible NMIs
out 72h,al
Skip_NMIS: ;3.30
cli ; disable and mask
mov al,0ffh ; all other ints
out 021h,al
out 0a1h,al
mov si,cs
mov ds,si
mov si,offset fatal_msg
fatal_loop:
lodsb
cmp al,'$'
je fatal_done
mov bl,7 ;3.30*
mov ah,14 ;3.30*
int 010h ; whoops, this enables ints ;3.30*
jmp fatal_loop
fatal_done:
jmp fatal_done
fatal endp

297
v4.0/src/BIOS/MSVOLID.INC Normal file
View File

@ -0,0 +1,297 @@
;-------------------------------------------------------------------------
;
; File: msvolid.asm
; This file contains the volume_id subroutines and data structures.
;
; Routines in this file are:
; Set_Volume_ID - main routine, calls other routines.
; read_volume_id - read the volume ID and tells if it has
; been changed.
; Transfer_volume_id - copy the volume ID from TMP to special
; drive.
; Check_Volume_ID - compare volume ID in TMP area with one
; expected for drive.
; Fat_Check - see of the fatID has changed in the
; specified drive.
; Init_Vid_loop - set up for VID scan or move
;
;
;-------------------------------------------------------------------------
;
; length of the volume id
;
vid_size equ 12
PATHSTART 001,VOLID ;3.30
;
; null volume id
;
nul_vid db "NO NAME ",0
;
; data scratch area used to hold volume ids
;
tmp_vid db "NO NAME ",0
PATHEND 001,VOLID ;3.30
;
; Set_Volume_ID
; If drive has changeline support, read in and set the volume_ID
; and the last FAT_ID byte. If no change line support then do nothing.
;
; On entry:
; DS:DI points to the BDS for this disk.
; AH contains media byte
;
; On Exit:
; Carry clear:
; Successful call
; Carry set
; Error and AX has error code
;
Set_Volume_ID:
PUBLIC SET_VOLUME_ID ;3.30
push dx ; save registers
push ax
CALL HasChange ; does drive have changeline support?
jz setvret ; no, get out
push di
call read_volume_ID ; read the volume ID
pop di
jc SetErr ; if error go to error routine
call transfer_volume_ID ; copy the volume id to special drive
call ResetChanged ; restore value of change line
setvret: ; SET Volume RETurn
clc ; no error, clear carry flag
pop ax ; restore registers
pop dx
ret
SetErr:
pop dx ; pop stack but don't overwrite AX
pop dx ; restore DX
ret
root_sec DW ? ;Root sector #
;
; read_volume_id read the volume ID and tells if it has been changed.
;
; On entry:
; DS:DI points to current BDS for drive.
; On Exit:
; Carry Clear
; SI = 1 No change
; SI = 0 ?
; SI = -1 Change
;
; Carry Set:
; Error and AX has error code.
;
read_volume_id:
push ES ; preserve registers
push DX
push CX
push BX
push AX
push DS ; Preserve Current BDS
push DI
push cs ; get ES segment correct
pop es
push cs ; get DS segment correct
pop ds
mov di,offset tmp_vid
mov si,offset nul_vid
mov cx,vid_size
rep movsb ; initialize tmp_vid to null vi_id
pop DI ; Restore Current BDS
pop DS
mov al,byte ptr ds:[di].cFAT ; # of fats
mov cx,word ptr ds:[di].csecfat ; sectors / fat
mul cl ; size taken by fats
add ax,word ptr ds:[di].ressec ; add on reserved sectors
; AX is now sector # (0 based)
mov cs:[root_sec],ax ; set initial value
mov ax,[di].cDir ; # root dir entries
mov cl,4 ; 16 entries/sector
shr ax,cl ; divide by 16
mov cx,ax ; cx is # of sectors to scan
next_sec:
push cx ; save outer loop counter
mov ax,cs:[root_sec] ; get sector #
mov cx,word ptr ds:[di].seclim ; sectors / track
xor DX,DX
div cx
; set up registers for call to read_sector
inc DX ; dx= sectors into track, ax= track count from 0
mov cl,dl ; sector to read
xor DX,DX
div word ptr ds:[di].hdlim ; # heads on this disc
mov dh,dl ; Head number
mov ch,al ; Track #
call read_sector ; get first sector of the root directory,
; ES:BX -> BOOT
jc ReadVIDErr ; error on read
mov cx,16 ; # of dir entries in a block of root
mov al,08h ; volume label bit
fvid_loop:
cmp byte ptr es:[bx],0 ; End of dir?
jz no_vid ; yes, no vol id
cmp byte ptr es:[bx],0E5h ; empty entry?
jz ent_loop ; yes, skip
test es:[bx+11],al ; is volume label bit set in fcb?
jnz found_vid ; jmp yes
ent_loop:
ADD BX,32 ;MJB003 ADD LENGTH OF DIRECTORY ENTRY ;3.30
loop fvid_loop
pop cx ; outer loop
inc cs:[root_sec] ; next sector
loop next_sec ; continue
NotFound:
XOR SI,SI
jmp short fvid_ret
found_vid:
pop cx ; clean stack of outer loop counter
mov si,bx ; point to volume_id
push ds ; preserve currnet BDS
push di
push es ; es:si points to volume id.
pop ds ; source segment
push cs
pop es ; destination segment
mov di,offset tmp_vid ; dest of volume_id
mov cx,vid_size -1 ; length of string minus NUL
rep movsb ; mov volume label to tmp_vid
xor al,al
stosb ; Null terminate
XOR SI,SI
pop DI ; restore current BDS
pop DS
fvid_ret:
pop ax
clc
RVIDRet:
pop BX ; restore register
pop CX
pop DX
pop ES
ret
no_vid:
pop cx ; clean stack of outer loop counter
jmp NotFound ; not found
ReadVIDErr:
pop SI
pop SI
jmp RVIDRet
;
; Transfer_volume_id - copy the volume ID from TMP to special drive
;
; Inputs: DS:DI nas current BDS
; Outputs: BDS for drive has volume ID from TMP
;
transfer_volume_ID:
push DS ; preserve current BDS
push DI
push ES
push SI
push CX
call init_vid_loop
cld
rep MOVSB ; transfer
pop CX
pop SI
pop ES
pop DI ; restore current BDS
pop DS
ret
;
; Check_Volume_ID - compare volume ID in TMP area with one expected for
; drive
;
; Inputs: DS:DI has current BDS for drive
; Outputs: SI = 0 if compare succeeds
; SI = -1 if compare fails.
check_volume_id:
push DS ; preserve current BDS for drive
push DI
push ES
push CX
call init_vid_loop
cld
repz cmpsb ; are the 2 volume_ids the same?
mov si,0 ; assume unknown
jz check_vid_ret ; carry clear if jump taken
mov si,-1 ; failure
check_vid_ret:
pop CX
pop ES
pop DI ; restore current BDS
pop DS
ret
;
; Fat_Check - see of the fatID has changed in the specified drive.
; - uses the FAT ID obtained from the boot sector.
;
; Inputs: MedByt is expected FAT ID
; DS:DI points to current BDS
; Output: Carry Clear
; SI = -1 if fat ID different,
; SI = 0 otherwise
; No other registers changed.
FAT_CHECK:
push AX
xor SI, SI ; say FAT ID's are same.
mov AL, cs:MedByt
cmp AL, byte ptr [DI].Mediad ; compare it with the BDS medbyte
jz OKRET1 ; carry clear
dec SI
OkRet1: clc
pop AX
ret
;
; Init_Vid_loop - set up for VID scan or move
;
; Inputs: DS:DI pionts to BDS for the drive
; Outputs: DS:SI points to tmp_vid
; ES:DI points to vid for drive
; CX has size for VID compare
;
init_vid_loop:
push ax
push ds
pop es
push cs
pop ds
mov si,offset tmp_vid ; source
add di,volid
mov cx,vid_size
pop ax
ret

View File

@ -0,0 +1,63 @@
;*******************************************************************
; Parser Options set for IBMBIO SYSCONF module
;*******************************************************************
;
;**** Default assemble swiches definition **************************
IFNDEF FarSW
FarSW equ 0 ; Near call expected
ENDIF
IFNDEF DateSW
DateSW equ 0 ; Check date format
ENDIF
IFNDEF TimeSW
TimeSW equ 0 ; Check time format
ENDIF
IFNDEF FileSW
FileSW equ 1 ; Check file specification
ENDIF
IFNDEF CAPSW
CAPSW equ 0 ; Perform CAPS if specified
ENDIF
IFNDEF CmpxSW
CmpxSW equ 0 ; Check complex list
ENDIF
IFNDEF NumSW
NumSW equ 1 ; Check numeric value
ENDIF
IFNDEF KeySW
KeySW equ 0 ; Support keywords
ENDIF
IFNDEF SwSW
SwSW equ 1 ; Support switches
ENDIF
IFNDEF Val1SW
Val1SW equ 1 ; Support value definition 1
ENDIF
IFNDEF Val2SW
Val2SW equ 0 ; Support value definition 2
ENDIF
IFNDEF Val3SW
Val3SW equ 1 ; Support value definition 3
ENDIF
IFNDEF DrvSW
DrvSW equ 1 ; Support drive only format
ENDIF
IFNDEF QusSW
QusSW equ 0 ; Support quoted string format
ENDIF


20
v4.0/src/BIOS/PUSHPOP.INC Normal file
View File

@ -0,0 +1,20 @@
IF1 ;3.30
SaveReg MACRO reglist ;; push those registers
IRP reg,<reglist>
?stackdepth = ?stackdepth + 1
PUSH reg
ENDM
ENDM
.xcref SaveReg
RestoreReg MACRO reglist ;; pop those registers
IRP reg,<reglist>
?stackdepth = ?stackdepth - 1
POP reg
ENDM
ENDM
.xcref RestoreReg
ENDIF ;3.30

165
v4.0/src/BIOS/READCLOC.INC Normal file
View File

@ -0,0 +1,165 @@
; SCCSID = @(#)readclock.asm 1.2 85/07/25
;************************************************************************
;
; read_real_date reads real-time clock for date and returns the number
; of days elapsed since 1-1-80 in si
;
read_real_date: ;mjb002
assume ds:code,es:nothing
PUSH AX
PUSH CX
PUSH DX
XOR AH,AH ; throw away clock roll over ;3.30*
INT 1AH ;3.30*
POP DX
POP CX
POP AX
PUSH AX
PUSH BX
PUSH CX
PUSH DX
MOV CS:DAYCNT2,1 ;MJB002 REAL TIME CLOCK ERROR FLAG (+1 DA;3.30Y)
mov ah,4 ;mjb002 read date function code ;3.30*
int 1ah ;mjb002 read real-time clock ;3.30*
jnc read_ok ;mjb002 jmp success
jmp r_d_ret ;mjb002 jmp error
read_ok: ;mjb002 ******* get bcd values in binary *****
mov byte ptr bin_date_time+0,ch ;mjb002 store as hex value
mov byte ptr bin_date_time+1,cl ;mjb002 ...
mov byte ptr bin_date_time+2,dh ;mjb002 ...
mov byte ptr bin_date_time+3,dl ;mjb002 ...
MOV CS:DAYCNT2,2 ;MJB002 READ OF R-T CLOCK SUCCESSFUL ;3.30
call bcd_verify ;mjb002 verify bcd values in range
jc r_d_ret ;mjb002 jmp some value out of range
MOV CS:DAYCNT2,3 ;MJB002 READ OF R-T CLOCK SUCCESSFUL ;3.30
call date_verify ;mjb002 verify date values in range
jc r_d_ret ;mjb002 jmp some value out of range
MOV CS:DAYCNT2,0 ;MJB002 VERIFY SUCCESSFUL ;3.30;3.30
call in_bin ;mjb002 convert date to binary
;mjb002 ******* years since 1-1-80 *********
mov al,byte ptr bin_date_time+1 ;mjb002 get years into century
cbw ;mjb002
cmp byte ptr bin_date_time+0,20 ;mjb002 20th century?
jnz century_19 ;mjb002 jmp no
add ax,100 ;mjb002 add in a century
century_19: ;mjb002
sub ax,80 ;mjb002 subtract off 1-1-80
mov cl,4 ;mjb002 leap year every 4
div cl ;mjb002 al= # leap year blocks, ah= remainder
mov bl,ah ;mjb002 save odd years
cbw ;mjb002 zero ah
mov cx,366+3*365 ;mjb002 # of days in leap year blocks
mul cx ;mjb002 dx:ax is result
MOV CS:DAYCNT2,AX ;MJB002 SAVE COUNT OF DAYS ;3.30
mov al,bl ;mjb002 get odd years count
cbw ;mjb002
or ax,ax ;mjb002 is ax= 0?
jz leap_year ;mjb002 jmp if none
mov cx,365 ;mjb002 days in year
mul cx ;mjb002 dx:ax is result
ADD CS:DAYCNT2,AX ;MJB002 ADD ON DAYS IN ODD YEARS ;3.30
jmp short leap_adjustment ;mjb002 account for leap year
leap_year: ;mjb002 possibly account for a leap day
cmp byte ptr bin_date_time+2,2 ;mjb002 is month february
jbe no_leap_adjustment ;mjb002 jan or feb. no leap day yet.
leap_adjustment: ;mjb002 account for leap day
INC CS:DAYCNT2 ;MJB002 ... ;3.30
no_leap_adjustment: ;mjb002 ******* get days of month *******
mov cl,byte ptr bin_date_time+3 ;mjb002 ...
xor ch,ch ;mjb002
dec cx ;mjb002 because of offset from day 1, not day 0
ADD CS:DAYCNT2,CX ;MJB002 ******* GET DAYS IN MONTHS PRECEE;3.30DING *****
mov cl,byte ptr bin_date_time+2 ;mjb002 get month
xor ch,ch ;mjb002
dec cx ;mjb002 january starts at offset 0
shl cx,1 ;mjb002 word offset
mov si,offset month_table ;mjb002 beginning of month_table
add si,cx ;mjb002 point into month table
mov ax,word ptr [si];mjb002 get # days in previous months
ADD CS:DAYCNT2,AX ;MJB002 ... ;3.30
r_d_ret: ;mjb002
MOV SI,CS:DAYCNT2 ;MJB002 RESULT IN SI ;3.30
POP DX
POP CX
POP BX
POP AX
ret ;mjb002
r_t_retj:
xor cx,cx
xor dx,dx
jmp r_t_ret
;
; Read_Real_Time reads the time from the RTC. on exit, it has the number of
; ticks (at 18.2 ticks per sec.) in CX:DX.
;
Read_Real_Time:
mov ah,2 ;3.30*
int 1AH ;3.30*
jc r_t_retj
oktime:
mov byte ptr bin_date_time,ch ; hours
mov byte ptr bin_date_time+1,cl ; minutes
mov byte ptr bin_date_time+2,dh ; seconds
mov byte ptr bin_date_time+3,0 ; unused for time
call bcd_verify
jc r_t_retj
call time_verify
jc r_t_retj
call in_bin
MOV ch,byte ptr bin_date_time
MOV cl,byte ptr bin_date_time+1
MOV dh,byte PTR bin_date_time+2
MOV dl,byte PTR bin_date_time+3
message ftestinit,<"Read Time ">
mnum ftestinit,cx
message ftestinit,<" ">
mnum ftestinit,dx
message ftestinit,<cr,lf>
; get time in ticks in CX:DX
CALL word ptr cs:TimeToTicks ;3.30
message ftestinit,<"Conv Time ">
mnum ftestinit,cx
message ftestinit,<" ">
mnum ftestinit,dx
message ftestinit,<cr,lf>
r_t_ret:
ret
;
; in_bin converts bin_date_time values from bcd to bin
;
in_bin: ;mjb002
assume ds:code,es:nothing
mov al,byte ptr bin_date_time+0 ; century or hours
call bcd_to_bin ; ...
mov byte ptr bin_date_time+0,al ;
mov al,byte ptr bin_date_time+1 ; years or minutes
call bcd_to_bin ; ...
mov byte ptr bin_date_time+1,al ;
mov al,byte ptr bin_date_time+2 ; months or seconds
call bcd_to_bin ; ...
mov byte ptr bin_date_time+2,al ;
mov al,byte ptr bin_date_time+3 ; days (not used for time)
call bcd_to_bin ; ...
mov byte ptr bin_date_time+3,al ;
ret ;
;
; bcd_to_bin converts two bcd nibbles in al (value <= 99.) to
; a binary representation in al
; ah is destroyed
;
bcd_to_bin: ;mjb002
assume ds:nothing,es:nothing
mov ah,al ;mjb002 copy bcd number to ah
and ax,0f00fh ;mjb002 clear unwanted nibbles
mov bl,al ;mjb002 save units place
xchg ah,al ;mjb002 10's place to al
xor ah,ah ;mjb002 ah not wanted
mov cl,4 ;mjb002 shift count
shr ax,cl ;mjb004 swap nibbles
mov cl,10 ;mjb002 convert al to ...
mul cl ;mjb002 ... its binary value
add al,bl ;mjb002 add in units
ret ;mjb002

271
v4.0/src/BIOS/STKINIT.INC Normal file
View File

@ -0,0 +1,271 @@
;
; To follow the standard interrupt sharing scheme, MSSTACK.ASM ;3.30
; has been modified. This initialization routine also has to ;3.30
; be modified because for the interrupt level 7 and 15, FirstFlag ;3.30
; should be set to signal that this interrupt handler is the ;3.30
; first handler hooked to this interrupt vector. ;3.30
; We determine this by looking at the instruction pointed by ;3.30
; this vector. If it is IRET, then this handler should be the ;3.30
; first one. In our case, only the interrupt vector 77h is the ;3.30
; interrupt level 15. (We don't hook interrupt level 7.) ;3.30
; 9/10/1986 ;3.30
; The followings are mainly due to M.R.T; PTM fix of P886 12/3/86;3.30
; Some design changes are needed to the above interrupt sharing ;3.30
; method. The above sharing scheme assumes that 1). Interrupt ;3.30
; sharing is NEVER done on levels that have BIOS support. 2). "Phantom" ;3.30
; interrupts would only be generated on levels 7 and 15. ;3.30
; These assumptions are not true any more. We have to use the FirstFlag ;3.30
; for EVERY level of interrupt. We will set the firstFlag on the following;3.30
; conditions: ;3.30
; a. if the CS portion of the vector is 0000, then "first" ;3.30
; b. else if CS:IP points to valid shared header, then NOT "first" ;3.30
; c. else if CS:IP points to an IRET, then "first" ;3.30
; d. else if CS:IP points to DUMMY, then "first" ;3.30
; where DUMMY is - the CS portion must be F000, and the IP portion must ;3.30
; be equal to the value at F000:FF01. This location is the initial value ;3.30
; from VECTOR_TABLE for interrupt 7, one of the preserved addresses in all;3.30
; the BIOSes for all of the machines. ;3.30
; ;3.30
; System design group requests BIOS to handle the phantom interrupts. ;3.30
; ;3.30
; The "Phantom" interrupt is an illegal interrupt such as an interrupt ;3.30
; produced by the bogus adapter card even without interrupt request is ;3.30
; set. More specifically, 1). The 8259 has a feature when running in ;3.30
; edge triggered mode to latch a pulse and present the interrupt when ;3.30
; the processor indicates interrupt acknowledge (INTA). The interrupt ;3.30
; pulse was exist at the time of INTA to get a "phantom" interrupt. ;3.30
; 2). or, this is caused by adapter cards placing a glitch on the ;3.30
; interrupt line. ;3.30
; ;3.30
; To handle those "phantom" interrupts, the main stack code will check ;3.30
; the own FirstFlag, and if it is not "first" (which means the forward ;3.30
; pointer points to the legal shared interrupt handler), then pass the ;3.30
; control. If it is the first, then the following action should be ;3.30
; taken. We don't have to implement skack logic in this case. ;3.30
; ;3.30
; To implement this logic, we rather choose a simple method. ;3.30
; If ont of the above "FirstFlag" conditions is met, we are not ;3.30
; going to hook this interrupt vector. The reason is if the original ;3.30
; vector points to "IRET" and do nothing, we don't need ;3.30
; to implement the stack logic for it. This will simplify implementation;3.30
; while maintaining compatibility with the old version of DOS. ;3.30
; This implies that in the main stack code, there might be a stack code ;3.30
; that will never be used, a dead code. ;3.30
; ;3.30
; 12/3/86 ;3.30
;3.30
;In - CS, DS -> sysinitseg, ES -> relocated stack code & data. ;3.30
;3.30
PAGE ;3.30
assume ds:sysinitseg ; sunilp SB340
StackInit proc near ;3.30
;3.30
PUSH AX ;SAVE ALL ;3.30
PUSH DS ;3.30
PUSH ES ;3.30
PUSH BX ;3.30
PUSH CX ;3.30
PUSH DX ;3.30
PUSH DI ;3.30
PUSH SI ;3.30
PUSH BP ;3.30
;3.30
;Currently ES -> stack code area ;3.30
MOV AX, cs:[STACK_COUNT] ;defined in CS ;3.30
MOV es:[STACKCOUNT], AX ;defined in STACK CODE AREA ;3.30
MOV AX, [STACK_SIZE] ;in CS ;3.30
MOV es:[STACKSIZE], AX ; ;3.30
MOV AX, WORD PTR cs:[STACK_ADDR] ; OFFSET ;3.30
MOV WORD PTR es:[STACKS], AX ;3.30
MOV AX, WORD PTR cs:[STACK_ADDR+WORD] ; SEGMENT ;3.30
MOV WORD PTR es:[STACKS+WORD], AX ;3.30
;3.30
; INITIALIZE THE DATA FIELDS WITH THE PARAMETERS ;3.30
;3.30
; "FIRSTENTRY" WILL ALWAYS BE AT STACKS ;3.30
;3.30
MOV BP, word ptr es:STACKS ; GET OFFSET OF STACK ;3.30
MOV es:FIRSTENTRY,BP ;3.30
;3.30
; THE STACKS WILL ALWAYS IMMEDIATELY FOLLOW THE TABLE ENTRIES ;3.30
;3.30
MOV AX,ENTRYSIZE ;3.30
MOV CX,es:STACKCOUNT ;3.30
MUL CX ;3.30
ADD AX,BP ;3.30
MOV es:STACKAT,AX ;3.30
MOV BX,AX ;3.30
SUB BX,2 ;3.30
;3.30
; ZERO THE ENTIRE STACK AREA TO START WITH ;3.30
;3.30
MOV DI,es:STACKAT ;3.30
MOV AX,es:STACKSIZE ;3.30
MUL CX ;3.30
MOV CX,AX ;3.30
xor ax,ax ;3.30
push es ;3.30
pop ds ;ds = Relocated stack code seg.;3.30
assume ds:nothing ;3.30
;Now, DS -> stack code area ;3.30
MOV ES, word ptr ds:[STACKS+2] ; GET SEGMENT OF STACK AREA.;3.30
CLD ;3.30
REP STOSB ;3.30
;3.30
MOV CX, ds:STACKCOUNT ;3.30
;3.30
; LOOP FOR "COUNT" TIMES, BUILDING A TABLE ENTRY ;3.30
; cs = sysinitseg, ds = Relocated stack code seg , es = segment of stack space;3.30
; CX = NUMBER OF ENTRIES ;3.30
; ES:BP => BASE OF STACKS - 2 ;3.30
; ES:BX => FIRST TABLE ENTRY ;3.30
;3.30
BUILDLOOP: ;3.30
MOV ALLOCBYTE,FREE ;3.30
MOV INTLEVEL,AL ;AX = 0 ;3.30
MOV SAVEDSP,AX ;3.30
MOV SAVEDSS,AX ;3.30
ADD BX,ds:STACKSIZE ;3.30
MOV NEWSP,BX ;3.30
MOV ES:[BX],BP ;3.30
ADD BP,ENTRYSIZE ;3.30
;3.30
LOOP BUILDLOOP ;3.30
;3.30
SUB BP,ENTRYSIZE ;3.30
MOV ds:LASTENTRY,BP ;3.30
MOV ds:NEXTENTRY,BP ;3.30
;3.30
push ds ;3.30
mov ax, 0f000h ;loook at the model byte ;3.30
mov ds, ax ;3.30
cmp ds:byte ptr [0fffeh], mdl_convert ;convertible? ;3.30
pop ds ;3.30
jne Skip_disableNMIS ;3.30
;3.30
MOV AL,07H ; DISABLE Convertible NMIS ;3.30
OUT 72H,AL ;3.30
;3.30
Skip_disableNMIS: ;3.30
XOR AX,AX ;3.30
MOV es,AX ;es - SEGID OF VECTOR TABLE AT 0;3.30
ASSUME es:NOTHING ;ds - Relocated Stack code segment;3.30
;3.30
CLI ;3.30
;3.30
IRP AA,<02,08,09,70> ;3.30
;3.30
MOV SI,AA&H*4 ;PASS WHERE VECTOR IS TO BE ADJUSTED ;3.30
mov di, offset Int19OLD&AA ;we have to set OLD&AA for Int19 handler too.;3.30
MOV BX,OFFSET OLD&AA ;PASS WHERE TO SAVE ORIGINAL OWNER POINTER;3.30
MOV DX,OFFSET INT&AA ;PASS WHERE NEW HANDLER IS ;3.30
CALL NEW_INIT_LOOP ;ADJUST THE VECTOR TO NEW HANDLER, ;3.30
; SAVING POINTER TO ORIGINAL OWNER ;3.30
ENDM ;3.30
;3.30
IRP AA,<0A,0B,0C,0D,0E,72,73,74,76,77> ;shared interrupts ;3.30
;3.30
MOV SI,AA&H*4 ;PASS WHERE VECTOR IS TO BE ADJUSTED ;3.30
push ds ;save relocated stack code segment ;3.30
lds bx, es:[si] ;ds:bx -> original interrupt handler ;3.30
push ds ;3.30
pop dx ;dx = segment value ;3.30
cmp dx,0
jz int&AA&_first
cmp byte ptr ds:[bx],0cfh ;Does vector point to an IRET?
jz int&AA&_first
cmp word ptr ds:[bx.6],424Bh ;Magic offset (see INT&AA, msstack.inc)
jz int&AA&_Not_first
cmp dx,0f000h ;ROM BIOS segment
jnz int&AA&_Not_first
push es
push dx
mov dx,0f000h
mov es,dx
cmp bx,word ptr es:0ff01h
pop dx
pop es
jz int&AA&_first
int&AA&_Not_first: ;Not the first. We are going to hook vector.;3.30
pop ds ;3.30
mov di, offset Int19OLD&AA ;we have to set OLD&AA for Int19 handler too.;3.30
mov BX, OFFSET OLD&AA ;PASS WHERE TO SAVE ORIGINAL OWNER POINTER;3.30
MOV DX, OFFSET INT&AA ;PASS WHERE NEW HANDLER IS ;3.30
CALL NEW_INIT_LOOP ;ADJUST THE VECTOR TO NEW HANDLER, SAVING;3.30
;POINTER TO ORIGINAL OWNER. ;3.30
jmp short int&AA&_end ;3.30
int&AA&_first: ;the first. Don't have to hook stack code.;3.30
pop ds ;3.30
int&AA&_end: ;3.30
;3.30
ENDM ;3.30
;3.30
push ds ;3.30
mov ax, 0f000h ;loook at the model byte ;3.30
mov ds, ax ;3.30
cmp ds:byte ptr [0fffeh], mdl_convert ;PC convertible? ;3.30
pop ds ;3.30
jne Skip_EnableNMIS ;3.30
;3.30
MOV AL,27H ; ENABLE Convertible NMIS ;3.30
OUT 72H,AL ;3.30
;3.30
Skip_EnableNMIS: ;3.30
STI ;3.30
MOV AX,code ;3.30
MOV DS,AX ;3.30
ASSUME DS:CODE ;3.30
;3.30
; MOV SI,OFFSET STKMSG1 ;3.30
; CALL WRMSG ;3.30
;3.30
mov [INT19SEM],1 ; INDICATE THAT INT 19 ;3.30
; INITIALIZATION IS COMPLETE ;3.30
;3.30
POP BP ; RESTORE ALL ;3.30
POP SI ;3.30
POP DI ;3.30
POP DX ;3.30
POP CX ;3.30
POP BX ;3.30
;3.30
POP ES ;3.30
POP DS ;3.30
assume ds:sysinitseg ;3.30
POP AX ;3.30
RET ;3.30
STACKINIT ENDP ;3.30
; ;3.30
;3.30
NEW_INIT_LOOP PROC NEAR ;3.30
;INPUT: SI=OFSET INTO VECTOR TABLE OF THE PARTICULAR INT VECTOR BEING ADJUSTED ;3.30
; BX=ds:OFFSET OF OLDxx, WHERE WILL BE SAVED THE POINTER TO ORIGINAL OWNER;3.30
; DX=ds:OFFSET OF INTxx, THE NEW INTERRUPT HANDLER ;3.30
; di=offset value of Int19OLD&AA variable in BIOS. ;3.30
; es=ZERO, SEGID OF VECTOR TABLE ;3.30
; ds=Relocated Stack code segment ;3.30
;3.30
MOV AX,es:[SI+0] ;REMEMBER OFFSET IN VECTOR ;3.30
MOV WORD PTR ds:[BX],AX ; TO ORIGINAL OWNER in DS ;3.30
MOV AX,es:[SI+2] ;REMEMBER SEGID IN VECTOR ;3.30
MOV WORD PTR ds:[BX]+2,AX ; TO ORIGINAL OWNER in DS ;3.30
push ds ;3.30
mov ax, code ;3.30
mov ds, ax ;Set Int19OLDxx value in BIOS for ;3.30
mov ax,es:[si+0] ;Int 19 handler ;3.30
mov word ptr ds:[di],ax ;3.30
mov ax,es:[si+2] ;3.30
mov word ptr ds:[di]+2,ax ;3.30
pop ds ;3.30
;3.30
MOV WORD PTR es:[SI+0],DX ;SET VECTOR TO POINT TO NEW INT HANDLER ;3.30
MOV es:[SI+2],ds ;3.30
RET ;3.30
NEW_INIT_LOOP ENDP ;3.30
;3.30

3392
v4.0/src/BIOS/SYSCONF.ASM Normal file

File diff suppressed because it is too large Load Diff

38
v4.0/src/BIOS/SYSIMES.ASM Normal file
View File

@ -0,0 +1,38 @@
;SCCSID = @(#)sysimes.asm 1.2 85/07/25
%OUT ...SYSIMES
;==============================================================================
;REVISION HISTORY:
;AN000 - New for DOS Version 4.00 - J.K.
;AC000 - Changed for DOS Version 4.00 - J.K.
;AN00x - PTM number for DOS Version 4.00 - J.K.
;==============================================================================
;AN001 D246, P976 Show "Bad command or parameters - ..." msg 9/22/87 J.K.
;AN002 P1820 New Message SKL file 10/20/87 J.K.
;AN003 D486 Share installation for large media 02/24/88 J.K.
;==============================================================================
iTEST = 0
include MSequ.INC
include MSmacro.INC
SYSINITSEG SEGMENT PUBLIC BYTE 'SYSTEM_INIT'
PUBLIC BADOPM,CRLFM,BADSIZ_PRE,BADLD_PRE,BADCOM,SYSSIZE,BADCOUNTRY
; PUBLIC BADLD_POST,BADSIZ_POST,BADMEM,BADBLOCK,BADSTACK
PUBLIC BADMEM,BADBLOCK,BADSTACK
PUBLIC INSUFMEMORY,BADCOUNTRYCOM
public BadOrder,Errorcmd ;AN000;
public BadParm ;AN001;
public SHAREWARNMSG ;AN003;
;include sysimes.inc
include MSbio.cl3 ;AN002;
SYSSIZE LABEL BYTE
PATHEND 001,SYSMES
SYSINITSEG ENDS
END

2668
v4.0/src/BIOS/SYSINIT1.ASM Normal file

File diff suppressed because it is too large Load Diff

1624
v4.0/src/BIOS/SYSINIT2.ASM Normal file

File diff suppressed because it is too large Load Diff

8
v4.0/src/BOOT/BOOT.SKL Normal file
View File

@ -0,0 +1,8 @@
:class 1
; MESSAGES FOR THE IBM BOOT SECTOR. NUL Terminated.
; At this time, for DOS 4.00, we only have maximum 11 bytes left
; for translation.!!!!!!!!!!!!!!!!!!!!!
:use 001 BOOT SYSMSG
:end

25
v4.0/src/BOOT/MAKEFILE Normal file
View File

@ -0,0 +1,25 @@
#******************** makefile for boot *****************************
msg =..\messages
dos =..\dos
inc =..\inc
hinc =..\h
#
#################### dependencies begin here ############################
#
all: msboot.bin
boot.cl1: boot.skl \
$(msg)\$(COUNTRY).MSG \
makefile
msboot.obj: msboot.asm boot.cl1
msboot.bin: msboot.obj
link msboot;
exe2bin msboot.exe msboot.bin
dbof msboot.bin boot.inc 7c00 200
copy boot.inc $(inc)
del boot.inc

530
v4.0/src/BOOT/MSBOOT.ASM Normal file
View File

@ -0,0 +1,530 @@
Page 60,132 ; SCCSID = @(#)msboot.asm 1.1 85/05/13
TITLE BOOT SECTOR 1 OF TRACK 0 - BOOT LOADER
; Rev 1.0 ChrisP, AaronR and others. 2.0 format boot
;
; Rev 3.0 MarkZ PC/AT enhancements
; 2.50 in label
; Rev 3.1 MarkZ 3.1 in label due to vagaries of SYSing to IBM drive D's
; This resulted in the BPB being off by 1. So we now trust
; 2.0 and 3.1 boot sectors and disbelieve 3.0.
;
; Rev 3.2 LeeAc Modify layout of extended BPB for >32M support
; Move PHYDRV to 3rd byte from end of sector
; so that it won't have to be moved again
; FORMAT and SYS count on PHYDRV being in a known location
;
; Rev. 3.3 D.C. L. Changed Sec 9 EOT field from 15 to 18. May 29, 1986.
;
; Rev 3.31 MarkT The COUNT value has a bogus check (JBE????) to determine
; if we've loaded in all the sectors of IBMBIO. This will
; cause too big of a load if the sectors per track is high
; enough, causing either a stack overflow or the boot code
; to be overwritten.
;
; Rev 4.00 J. K. For DOS 4.00 Modified to handle the extended BPB, and
; 32 bit sector number calculation to enable the primary
; partition be started beyond 32 MB boundary.
;
;
; The ROM in the IBM PC starts the boot process by performing a hardware
; initialization and a verification of all external devices. If all goes
; well, it will then load from the boot drive the sector from track 0, head 0,
; sector 1. This sector is placed at physical address 07C00h. The initial
; registers are set up as follows: CS=DS=ES=SS=0. IP=7C00h, SP=0400H.
;
; The code in this sector is responsible for locating the MSDOS device drivers
; (IBMBIO) and for placing the directory sector with this information at
; physical address 00500h. After loading in this sector, it reads in the
; entirety of the BIOS at BIOSEG:0 and does a long jump to that point.
;
; If no BIOS/DOS pair is found an error message is displayed and the user is
; prompted to reinsert another disk. If there is a disk error during the
; process, a message is displayed and things are halted.
;
; At the beginning of the boot sector, there is a table which describes the
; MSDOS structure of the media. This is equivalent to the BPB with some
; additional information describing the physical layout of the driver (heads,
; tracks, sectors)
;
;==============================================================================
;REVISION HISTORY:
;AN000 - New for DOS Version 4.00 - J.K.
;AC000 - Changed for DOS Version 4.00 - J.K.
;AN00x - PTM number for DOS Version 4.00 - J.K.
;==============================================================================
;AN001; d52 Make the fixed positioned variable "CURHD" to be local. 7/6/87 J.K.
;AN002; d48 Change head settle at boot time. 7/7/87 J.K.
;AN003; P1820 New message SKL file 10/20/87 J.K.
;AN004; D304 New structrue of Boot record for OS2. 11/09/87 J.K.
;==============================================================================
ORIGIN EQU 7C00H ; Origin of bootstrap LOADER
BIOSEG EQU 70H ; destingation segment of BIOS
BioOff EQU 700H ; offset of bios
cbSec EQU 512
cbDirEnt EQU 32
DirOff EQU 500h
IBMLOADSIZE equ 3 ;J.K. Size of IBMLOAD module in sectors
ROM_DISKRD equ 2
include version.inc
;
; Define the destination segment of the BIOS, including the initialization
; label
;
SEGBIOS SEGMENT AT BIOSEG
BIOS LABEL BYTE
SEGBIOS ENDS
CODE SEGMENT
ASSUME CS:CODE,DS:NOTHING,ES:NOTHING,SS:NOTHING
; ORG DirOff + 1Ch
;BiosFS LABEL WORD
ORG ORIGIN
DSKADR = 1EH*4 ;POINTER TO DRIVE PARAMETERS
Public $START
$START:
JMP START
;----------------------------------------------------------
;
; THE FOLLOWING DATA CONFIGURES THE BOOT PROGRAM
; FOR ANY TYPE OF DRIVE OR HARDFILE
;
;J.K. Extened_BPB
if ibmcopyright
DB "IBM "
else
DB "MSDOS"
endif
DB "4.0" ;AN005;
ByteSec DW cbSec ; SIZE OF A PHYSICAL SECTOR
DB 8 ; SECTORS PER ALLOCATION UNIT
cSecRes DW 1 ; NUMBER OF RESERVED SECTORS
cFat DB 2 ; NUMBER OF FATS
DirNum DW 512 ; NUMBER OF DIREC ENTRIES
cTotSec DW 4*17*305-1 ; NUMBER OF SECTORS - NUMBER OF HIDDEN SECTORS
; (0 when 32 bit sector number)
MEDIA DB 0F8H ; MEDIA BYTE
cSecFat DW 8 ; NUMBER OF FAT SECTORS
SECLIM DW 17 ; SECTORS PER TRACK
HDLIM DW 4 ; NUMBER OF SURFACES
Ext_cSecHid label dword
cSecHid_L DW 1 ;AN000; NUMBER OF HIDDEN SECTORS
cSecHid_H dw 0 ;AN000; high order word of Hiden Sectors
Ext_cTotSec label dword
ctotsec_L dw 0 ;AN000; 32 bit version of NUMBER OF SECTORS
ctotsec_H dw 0 ;AN000; (when 16 bit version is zero)
;
Phydrv db 80h ;AN004;
Curhd db 0h ;AN004; Current Head
Ext_Boot_Sig db 41 ;AN000;
Boot_Serial dd 0 ;AN000;
Boot_Vol_Label db 'NO NAME ' ;AN000;
Boot_System_id db 'FAT12 ' ;AN000;
;J.K. Danger!!! If not 32 bit sector number calculation, FORMAT should
;set the value of cSecHid_h and Ext_cTotSec to 0 !!!
;
;
Public UDATA
UDATA LABEL byte
Sec9 equ byte ptr UDATA+0 ;11 byte diskette parm. table
BIOS$_L EQU WORD PTR UDATA+11
BIOS$_H equ word ptr UDATA+13 ;AN000;
CURTRK EQU WORD PTR UDATA+15
CURSEC EQU BYTE PTR UDATA+17
DIR$_L EQU WORD PTR UDATA+18
Dir$_H equ word ptr UDATA+20 ;AN000;
START:
;
; First thing is to reset the stack to a better and more known place. The ROM
; may change, but we'd like to get the stack in the correct place.
;
CLI ;Stop interrupts till stack ok
XOR AX,AX
MOV SS,AX ;Work in stack just below this routine
ASSUME SS:CODE
MOV SP,ORIGIN
PUSH SS
POP ES
ASSUME ES:CODE
;
; We copy the disk parameter table into a local area. We scan the table above
; for non-zero parameters. Any we see get changed to their non-zero values.
;
;J.K. We copy the disk parameter table into a local area (overlayed into the
;code), and set the head settle time to 1, and End of Track to SECLIM given
;by FORMAT.
MOV BX,DSKADR
LDS SI,DWORD PTR SS:[BX] ; get address of disk table
PUSH DS ; save original vector for possible
PUSH SI ; restore
PUSH SS
PUSH BX
MOV DI,offset Sec9
MOV CX,11
CLD
if $ le BIOS$_L
%OUT Don't destroy unexcuted code yet!!!
endif
repz movsb ;AN000;
push es ;AN000;
pop ds ;AN000; DS = ES = code = 0.
assume ds:code ;AN000;
; mov byte ptr [di-2], 1 ;AN000; Head settle time
;J.K. Change the head settle to 15 ms will slow the boot time quite a bit!!!
mov byte ptr [di-2], 0fh ;AN002; Head settle time
mov cx, SECLIM ;AN004;
mov byte ptr [di-7], cl ;AN000; End of Track
;
; Place in new disk parameter table vector.
;
MOV [BX+2],AX
MOV [BX],offset SEC9
;
; We may now turn interrupts back on. Before this, there is a small window
; when a reboot command may come in when the disk parameter table is garbage
;
STI ;Interrupts OK now
;
; Reset the disk system just in case any thing funny has happened.
;
INT 13H ;Reset the system
; JC RERROR
jc CKErr ;AN000;
;
; The system is now prepared for us to begin reading. First, determine
; logical sector numbers of the start of the directory and the start of the
; data area.
xor ax,ax ;AN000;
cmp cTotSec,ax ;AN000; 32 bit calculation?
je Dir_Cont ;AN000;
mov cx,cTotSec ;AN000;
mov cTotSec_L,cx ;AN000; cTotSec_L,cTotSec_H will be used for calculation
Dir_Cont: ;AN000;
MOV AL,cFat ;Determine sector dir starts on
MUL cSecFat ;DX;AX
ADD AX,cSecHid_L
adc DX,cSecHid_H ;AN000;
ADD AX,cSecRes
ADC DX,0
MOV [DIR$_L],AX ; DX;AX = cFat*cSecFat + cSecRes + cSecHid
mov [DIR$_H],DX ;AN000;
MOV [BIOS$_L],AX
mov [BIOS$_H],DX ;AN000;
;
; Take into account size of directory (only know number of directory entries)
;
MOV AX,cbDirEnt ; bytes per directory entry
MUL DirNum ; convert to bytes in directory
MOV BX,ByteSec ; add in sector size
ADD AX,BX
DEC AX ; decrement so that we round up
DIV BX ; convert to sector number
ADD [BIOS$_L],AX ; Start sector # of Data area
adc [BIOS$_H],0 ;AN000;
;
; We load in the first directory sector and examine it to make sure the the
; BIOS and DOS are the first two directory entries. If they are not found,
; the user is prompted to insert a new disk. The directory sector is loaded
; into 00500h
;
MOV BX,DirOff ; sector to go in at 00500h
mov dx,[DIR$_H] ;AN000;
MOV AX,[DIR$_L] ; logical sector of directory
CALL DODIV ; convert to sector, track, head
jc CKErr ;AN000; Overflow? BPB must be wrong!!
; MOV AX,0201H ; disk read 1 sector
mov al, 1 ;AN000; disk read 1 sector
CALL DOCALL ; do the disk read
JB CKERR ; if errors try to recover
;
; Now we scan for the presence of IBMBIO COM and IBMDOS COM. Check the
; first directory entry.
;
MOV DI,BX
MOV CX,11
MOV SI,OFFSET BIO ; point to "ibmbio com"
REPZ CMPSB ; see if the same
JNZ CKERR ; if not there advise the user
;
; Found the BIOS. Check the second directory entry.
;
LEA DI,[BX+20h]
MOV SI,OFFSET DOS ; point to "ibmdos com"
MOV CX,11
REPZ CMPSB
JZ DoLoad
;
; There has been some recoverable error. Display a message and wait for a
; keystroke.
;
CKERR: MOV SI,OFFSET SYSMSG ; point to no system message
ErrOut: CALL WRITE ; and write on the screen
XOR AH,AH ; wait for response
INT 16H ; get character from keyboard
POP SI ; reset disk parameter table back to
POP DS ; rom
POP [SI]
POP [SI+2]
INT 19h ; Continue in loop till good disk
Load_Failure:
pop ax ;adjust the stack
pop ax
pop ax
jmp short Ckerr ;display message and reboot.
;J.K. We don't have the following error message any more!!!
;J.K. Sysmsg is fine. This will save space by eliminating DMSSG message.
;RERROR: MOV SI,OFFSET DMSSG ; DISK ERROR MESSAGE
; JMP ErrOut
;
; We now begin to load the BIOS in. Compute the number of sectors needed.
; J.K. All we have to do is just read in sectors contiguously IBMLOADSIZE
; J.K. times. We here assume that IBMLOAD module is contiguous. Currently
; J.K. we estimate that IBMLOAD module will not be more than 3 sectors.
DoLoad:
mov BX,BioOff ;offset of ibmbio(IBMLOAD) to be loaded.
mov CX,IBMLOADSIZE ;# of sectors to read.
mov AX, [BIOS$_L] ;Sector number to read.
mov DX, [BIOS$_H] ;AN000;
Do_While: ;AN000;
push AX ;AN000;
push DX ;AN000;
push CX ;AN000;
call DODIV ;AN000; DX;AX = sector number.
jc Load_Failure ;AN000; Adjust stack. Show error message
mov al, 1 ;AN000; Read 1 sector at a time.
;This is to handle a case of media
;when the first sector of IBMLOAD is the
;the last sector in a track.
call DOCALL ;AN000; Read the sector.
pop CX ;AN000;
pop DX ;AN000;
pop AX ;AN000;
jc CkErr ;AN000; Read error?
add AX,1 ;AN000; Next sector number.
adc DX,0 ;AN000;
add BX,ByteSec ;AN000; adjust buffer address.
loop Do_While ;AN000;
; MOV AX,BiosFS ; get file size
; XOR DX,DX ; presume < 64K
; DIV ByteSec ; convert to sectors
; INC AL ; reading in one more can't hurt
; MOV COUNT,AL ; Store running count
; MOV AX,BIOS$ ; get logical sector of beginning of BIOS
; MOV BIOSAV,AX ; store away for real bios later
; MOV BX,BioOff ; Load address from BIOSSEG
;
; Main read-in loop.
; ES:BX points to area to read.
; Count is the number of sectors remaining.
; BIOS$ is the next logical sector number to read
;
;LOOPRD:
; MOV AX,BIOS$ ; Starting sector
; CALL DODIV
;
; CurHD is the head for this next disk request
; CurTrk is the track for this next request
; CurSec is the beginning sector number for this request
;
; Compute the number of sectors that we may be able to read in a single ROM
; request.
;
; MOV AX,SECLIM
; SUB AL,CURSEC
; INC AX
;
; AX is the number of sectors that we may read.
;
;
;New code for Rev 3.31
;*****************************************************************************
; CMP COUNT,AL ;Is sectors we can read more than we need?
; JAE GOT_SECTORS ;No, it is okay
; MOV AL,COUNT ;Yes, only read in what is left
;GOT_SECTORS:
;*****************************************************************************
;End of change
;
; PUSH AX
; CALL DOCALL
; POP AX
; JB RERROR ; If errors report and go to ROM BASIC
; SUB COUNT,AL ; Are we finished?
;
;Old code replaced by Rev 3.3
;********************************************************************
; JBE DISKOK ; Yes -- transfer control to the DOS
;********************************************************************
;New code for Rev 3.3
;
; JZ DISKOK ; Yes -- transfer control to the DOS
;********************************************************************
;End of change
;
; ADD BIOS$,AX ; increment logical sector position
; MUL ByteSec ; determine next offset for read
; ADD BX,AX ; (BX)=(BX)+(SI)*(Bytes per sector)
; JMP LOOPRD ; Get next track
;
; IBMINIT requires the following input conditions:
;
; DL = INT 13 drive number we booted from
; CH = media byte
;J.K.I1. BX was the First data sector on disk (0-based)
;J.K.I1. IBMBIO init routine should check if the boot record is the
;J.K.I1. extended one by looking at the extended_boot_signature.
;J.K.I1. If it is, then should us AX;BX for the starting data sector number.
DISKOK:
MOV CH,Media
MOV DL,PhyDrv
MOV bx,[BIOS$_L] ;AN000; J.K.I1.Get bios sector in bx
mov ax,[BIOS$_H] ;AN000; J.K.I1.
JMP FAR PTR BIOS ;CRANK UP THE DOS
WRITE: LODSB ;GET NEXT CHARACTER
OR AL,AL ;clear the high bit
JZ ENDWR ;ERROR MESSAGE UP, JUMP TO BASIC
MOV AH,14 ;WILL WRITE CHARACTER & ATTRIBUTE
MOV BX,7 ;ATTRIBUTE
INT 10H ;PRINT THE CHARACTER
JMP WRITE
; convert a logical sector into Track/sector/head. AX has the logical
; sector number
; J.K. DX;AX has the sector number. Because of not enough space, we are
; going to use Simple 32 bit division here.
; Carry set if DX;AX is too big to handle.
;
DODIV:
cmp dx,Seclim ;AN000; To prevent overflow!!!
jae DivOverFlow ;AN000; Compare high word with the divisor.
DIV SECLIM ;AX = Total tracks, DX = sector number
INC DL ;Since we assume SecLim < 255 (a byte), DH =0.
;Cursec is 1-based.
MOV CURSEC, DL ;save it
XOR DX,DX
DIV HDLIM
MOV CURHD,DL ;Also, Hdlim < 255.
MOV CURTRK,AX
clc ;AN000;
ret ;AN000;
DivOverFlow: ;AN000;
stc ;AN000;
EndWR:
ret
;
;J.K.We don't have space for the following full 32 bit division.
; convert a logical sector into Track/sector/head. AX has the logical
; sector number
; J.K. DX;AX has the sector number.
;DODIV:
; push ax
; mov ax,dx
; xor dx,dx
; div SecLim
; mov Temp_H,ax
; pop ax
; div SecLim ;J.K.Temp_H;AX = total tracks, DX=sector
; INC DL ;Since we assume SecLim < 255 (a byte), DH =0.
; ;Cursec is 1-based.
; MOV CURSEC, DL ;save it
; push ax
; mov ax,Temp_H
; XOR DX,DX
; DIV HDLIM
; mov Temp_H,ax
; pop ax
; div HdLim ;J.K.Temp_H;AX=total cyliners,DX=head
; MOV CURHD,DL ;Also, Hdlim < 255.
; cmp Temp_H,0
; ja TooBigToHandle
; cmp ax, 1024
; ja TooBigToHandle
; MOV CURTRK,AX
;ENDWR: RET
;TooBigToHandle:
; stc
; ret
;
; Issue one read request. ES:BX have the transfer address, AL is the number
; of sectors.
;
DOCALL: MOV AH,ROM_DISKRD ;AC000;=2
MOV DX,CURTRK
MOV CL,6
SHL DH,CL
OR DH,CURSEC
MOV CX,DX
XCHG CH,CL
MOV DL, PHYDRV
mov dh, curhd
INT 13H
RET
; include ibmbtmes.inc
include boot.cl1 ;AN003;
IF IBMCOPYRIGHT
BIO DB "IBMBIO COM"
DOS DB "IBMDOS COM"
ELSE
BIO DB "IO SYS"
DOS DB "MSDOS SYS"
ENDIF
Free EQU (cbSec - 4) - ($-$start) ;AC000;
;Free EQU (cbSec - 5) - ($-$start)
if Free LT 0
%out FATAL PROBLEM:boot sector is too large
endif
org origin + (cbSec - 2) ;AN004;
; org origin + (cbSec - 5)
;Warning!! Do not change the position of following unless
;Warning!! you change BOOTFORM.INC (in COMMON subdirectory) file.
;Format should set this EOT value for IBMBOOT.
;FEOT db 12h ;AN000; set by FORMAT. AN004;Use SecLim in BPB instead.
; FORMAT and SYS count on CURHD,PHYDRV being right here
;J.K. CURHD has been deleted since it is not being used by anybody.
;CURHD DB ? ;AN001;Unitialized (J.K. Maybe don't need this).
;PHYDRV db 0 ;AN000;moved into the header part.
; Boot sector signature
db 55h,0aah
CODE ENDS
END


File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,24 @@
;-------------------------------------------------------------------
; message retriever skeleton file for APPEND
;-------------------------------------------------------------------
:util APPEND
:class a
;:use 1 COMMON1
:def 1 "Incorrect APPEND version",CR,LF
:def 2 "Invalid path",CR,LF
:def 3 "Invalid parameter",CR,LF
:def 4 "Invalid combination of parameters",CR,LF
:def 5 "No Append",CR,LF
:class b
:def 6 "APPEND / ASSIGN Conflict",CR,LF
:def 7 "APPEND / TopView Conflict",CR,LF
:def 8 "Incorrect DOS Version",CR,LF
:def 9 "APPEND already installed",CR,LF
;:use 8 COMMON1 ;"Incorrect DOS Version"
;:use 9 COMMON1 ;"APPEND already installed"
:end


View File

@ -0,0 +1,36 @@
page 60,120
; @@04 07/30/86 Fix second APPEND hang PTM P0000053
; @@05 08/13/86 Fix bad parm message PTM P0000125
; @@10 08/28/86 Change message for @@05 PTM P0000291
; @@11 09/10/86 Support message profile and make
; msg length variable. R.G. PTM P0000479
cseg segment public para 'CODE'
assume cs:cseg
public bad_append_msg ;@@11
public path_error_msg ;@@11
public parm_error_msg ;@@11
public path_parm_error_msg ;@@11
public no_append_msg ;@@11
public append_assign_msg ;@@11
public append_tv_msg ;@@11
public bad_DOS_msg ;@@11
public second_append_msg ;@@11
public len_bad_append_msg ;@@11
public len_path_error_msg ;@@11
public len_parm_error_msg ;@@11
public len_path_parm_error_msg ;@@11
public len_no_append_msg ;@@11
public len_append_assign_msg ;@@11
public len_append_tv_msg ;@@11
public len_bad_DOS_msg ;@@11
public len_second_append_msg ;@@11
cr equ 13
lf equ 10
include appendm.inc
cseg ends
end

View File

@ -0,0 +1,147 @@
INCSW EQU 0 ;INCLUDE PSDATA.INC ;AN000;
FARSW EQU 1 ;CALL THE PARSER BY NEAR CALL
DATESW EQU 0 ;SUPPRESS DATE CHECKING ;AN000;
TIMESW EQU 0 ;SUPPRESS TIME CHECKING ;AN000;
FILESW EQU 0 ;SUPPRESS CHECKING FILE SPECIFICATION ;AN000;
CAPSW EQU 0 ;SUPPRESS FILE TABLE CAPS ;AN000;
CMPXSW EQU 1 ;SUPPRESS CHECKING COMPLEX LIST
DRVSW EQU 1 ;SUPPRESS SUPPORT OF DRIVE ONLY FORMAT
QUSSW EQU 0 ;SUPPRESS SUPPORT OF QUOTED STRING FORMAT ;AN000;
NUMSW EQU 1 ;SUPPRESS CHECKING NUMERIC VALUE
KEYSW EQU 0 ;SUPPRESS KEYWORD SUPPORT ;AN000;
SWSW EQU 1 ;DO SUPPORT SWITCHES ;AN000;
VAL1SW EQU 0 ;SUPPRESS SUPPORT OF VALUE DEFINITION 1 ;AN000;
VAL2SW EQU 0 ;SUPPRESS SUPPORT OF VALUE DEFINITION 2 ;AN000;
VAL3SW EQU 1 ;DO SUPPORT VALUE DEFINITION 3
include psdata.inc
;***********************************************************************
;-------------------------------------------------------------------
;
; parser stuff for APPEND
;
;-------------------------------------------------------------------
p_block1 $P_PARMS_Blk <offset px_block1, 0, 0> ; parm block
p_block2 $P_PARMS_Blk <offset px_block2, 0, 0> ; parm block
;------------------------
; extended parameter block for APPEND first load
px_block1:
db 0 ; min number positional operands
db 0 ; max number positional operands
; dw 0 ; offset into control block for positionals
db 3 ; APPEND has two switches /E, /X, /PATH
dw offset e_switch ; control block for /E switch
dw offset x_switch ; control block for /X switch
dw offset path_switch ; control block for /PATH switch
db 0 ; max number of keywords
dw 0 ; offset of keyword control block
;------------------------
; extended parameter block for 2nd, 3rd, ... APPEND invocations
px_block2:
db 0 ; min number positional operands
db 1 ; max number positional operands
dw offset dirs_control ; pointer to dirs control block
; db 2 ; APPEND after first load has two switches /X, /PATH
db 3 ; APPEND has two switches /E, /X, /PATH
dw offset e_switch ; control block for /E switch
dw offset x_switch ; control block for /X switch
dw offset path_switch ; control block for /PATH switch
db 0 ; max number of keywords
;------------------------
dirs_control:
dw $P_Simple_S+$P_Optional ; complex, optional string
dw $P_CAP_File ; cap by file table
dw offset dirs_result ; dirs result buffer
dw offset dirs_values ; pointer to null value list
db 0 ; no synonyms
dirs_values:
db 0 ; null value list for dirs
;------------------------
x_switch:
dw $P_Simple_s+$P_Optional ; /X, /X:ON, /X:OFF simple, optional string
dw $P_CAP_Char ; cap by char table
dw offset x_result ; pointer to result block
dw offset x_values ; pointer to values block
db 1 ; number of switches and synonyms
db "/X",0 ; only /X is valid
x_values:
db 3 ; string values
db 0 ; zeroes here for ranges and
db 0 ; values
db 2 ; 2 possible string values
db 0 ; /X:OFF = 0
dw offset off_string ; pointer to "OFF"
db 1 ; /X:ON = 1
dw offset on_string
;------------------------
e_switch:
dw 0 ; /E
dw $P_CAP_Char ; cap by char table
dw offset e_result ; pointer to result block
dw offset e_values ; pointer to values block, none
db 1 ; number of switches and synonyms
db "/E",0 ; only /E is valid
e_values:
db 0 ; null value list for /E
;------------------------
path_switch:
dw $P_Simple_s ; /PATH:ON, /PATH:OFF simple string
dw $P_CAP_Char ; cap by char table
dw offset path_result ; pointer to result block
dw offset path_values ; pointer to values block
db 1 ; number of switches and synonyms
db "/PATH",0 ; only /PATH is valid
path_values:
db 3 ; string values
db 0 ; zeroes here for ranges and
db 0 ; values
db 2 ; 2 possible string values
db 0 ; /PATH:OFF = 0
dw offset off_string ; pointer to "OFF"
db 1 ; /PATH:ON = 1
dw offset on_string
;------------------------
off_string:
db "OFF",0 ; off string
on_string:
db "ON",0 ; on string
;------------------------
x_result $P_Result_Blk <> ; /X result block
e_result $P_Result_Blk <> ; /E result block
path_result $P_Result_Blk <> ; /PATH result block
dirs_result $P_Result_Blk <> ; dirs result block


View File

@ -0,0 +1,20 @@
#************************** makefile for cmd\append ***************************
msg =..\..\messages
dos =..\..\dos
inc =..\..\inc
hinc =..\..\h
#
####################### dependencies begin here. #########################
#
all: append.exe
append.ctl: append.skl $(msg)\$(COUNTRY).msg
append.obj: append.asm appendp.inc $(inc)\parse.asm append.ctl
append.exe: append.obj
link append;

View File

@ -0,0 +1,361 @@
;
; SYSTEM MACROS
;
; DISPLAY TEXT ON SCREEN
;
DISP MACRO TEXT,SEGM
IFNB <SEGM>
IFDIF <SEGM>,<DS>
PUSH DS
MOV AX,SEGM
MOV DS,AX
ENDIF
ENDIF
IFNB <TEXT>
LEA DX,TEXT
ENDIF
DOS DSTR
IFNB <SEGM>
IFDIF <SEGM>,<DS>
POP DS
ENDIF
ENDIF
ENDM
;
DMSG MACRO MSG
IFNB <MSG>
LEA DX,MSG
ENDIF
DISP
ENDM
;
DCHAR MACRO CHAR
PUSH DX
IFNB <CHAR>
MOV DL,CHAR ; SET CHARACTER
ELSE
MOV DL,AL
ENDIF
DOS DO
POP DX
ENDM
;
; CLEAR SCREEN
;
CLEAR MACRO
MOV CX,00H*256+00H ; ROW=00, COL=00
MOV DX,24H*256+79H ; ROW=24, COL=79
MOV BH,07H ; NORMAL ATTRIBUTE
MOV AX,06H*256+00H ; CLEAR WHOLE SCREEN
INT 10H
ENDM
;
POS MACRO ROW,COL,PAGE
IFNB <ROW>
MOV DX,ROW*256+COL ; SET ROW AND COLUMN
ENDIF
IFNB <PAGE>
MOV BH,PAGE ; SET PAGE
ELSE
MOV BH,0
ENDIF
MOV AH,02H ; POSTIION CURSOR
INT 10H
ENDM
;
DEFMSG MACRO ID,T1,T2,T3,T4,T5,T6,T7,T8,T9,T10
IFNB <ID>
ID LABEL BYTE ; DEFINE ESSAGE
ENDIF
IFNB <T1>
DB T1
ENDIF
IFNB <T2>
DB T2
ENDIF
IFNB <T3>
DB T3
ENDIF
IFNB <T4>
DB T4
ENDIF
IFNB <T5>
DB T5
ENDIF
IFNB <T6>
DB T6
ENDIF
IFNB <T7>
DB T7
ENDIF
IFNB <T8>
DB T8
ENDIF
IFNB <T9>
DB T9
ENDIF
IFNB <T10>
DB T10
ENDIF
DB '$'
ENDM
;
MOVE MACRO TO,LEN,FROM
IFNB <TO>
LEA DI,TO ; SET DESTINATION
ENDIF
IFNB <LEN>
MOV CX,LEN ; SET LENGTH
ENDIF
IFNB <FROM>
LEA SI,FROM ; SET SOURCE
ENDIF
REP MOVS BYTE PTR[DI],BYTE PTR[SI]
ENDM
MOVEZ MACRO TO,FROM
IFNB <TO>
LEA DI,TO ; SET DESTINATION
ENDIF
IFNB <FROM>
LEA SI,FROM ; SET SOURCE
ENDIF
CALL MOVZ$
ENDM
;
SCAN MACRO TO,LEN,VALUE,TYPE
IFNB <TO>
LEA DI,TO ; SET DESTINATION
ENDIF
IFNB <LEN>
MOV CX,LEN ; SET LENGTH
ENDIF
IFNB <VALUE>
MOV AL,VALUE ; SET SOURCE
ENDIF
IFB <TYPE>
REPZ SCASB
ENDIF
IFIDN <TYPE>,<EQ>
REPZ SCASB
ENDIF
IFIDN <TYPE>,<Z>
REPZ SCASB
ENDIF
IFIDN <TYPE>,<NE>
REPNZ SCASB
ENDIF
IFIDN <TYPE>,<NZ>
REPNZ SCASB
ENDIF
ENDM
;
FILL MACRO TO,LEN,VALUE
PUSH DI
PUSH CX
IFNB <TO>
LEA DI,TO ; SET DESTINATION
ENDIF
IFNB <LEN>
MOV CX,LEN ; SET LENGTH
ENDIF
IFNB <VALUE>
MOV AL,VALUE ; SET SOURCE
ENDIF
REP STOS BYTE PTR[DI]
POP CX
POP DI
ENDM
;
COMP MACRO TO,LEN,FROM
IFNB <TO>
LEA DI,TO ; SET DESTINATION
ENDIF
IFNB <LEN>
MOV CX,LEN ; SET LENGTH
ENDIF
IFNB <FROM>
LEA SI,FROM ; SET SOURCE
ENDIF
REPE CMPS BYTE PTR[DI],BYTE PTR[SI]
ENDM
COMPZ MACRO TO,FROM
IFNB <TO>
LEA DI,TO ; SET DESTINATION
ENDIF
IFNB <FROM>
LEA SI,FROM ; SET SOURCE
ENDIF
CALL CMPZ$
ENDM
;
XCHGS MACRO O1,O2
PUSH O1
PUSH O2
POP O1
POP O2
ENDM
;
JUMP MACRO COND,TARGET
LOCAL LAB
IFB <COND>
JMP TARGET
ENDIF
IFIDN <COND>,<A>
JNA LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NBE>
JBE LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<AE>
JNAE LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NB>
JB LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<B>
JNB LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NAE>
JAE LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<C>
JNC LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<BE>
JNBE LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NA>
JA LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<CXZ>
OR CX,CX
JNZ LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<E>
JNE LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<Z>
JNZ LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<G>
JNG LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NLE>
JLE LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<GE>
JNGE LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NL>
JL LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<L>
JNL LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NGE>
JGE LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<LE>
JNLE LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NG>
JG LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NC>
JC LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NE>
JE LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NZ>
JZ LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NO>
JO LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NP>
JP LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<PO>
JPE LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<NS>
JS LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<O>
JNO LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<P>
JNP LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<PE>
JPO LAB
JMP TARGET
LAB:
ENDIF
IFIDN <COND>,<S>
JNS LAB
JMP TARGET
LAB:
ENDIF
ENDM
;


File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,74 @@
BADDOS equ 1
STAT equ 2
PARSE01 equ 01
PARSE02 equ 02
PARSE03 equ 03
PARSE04 equ 04
PARSE05 equ 05
PARSE06 equ 06
PARSE07 equ 07
PARSE08 equ 08
PARSE09 equ 09
PARSE10 equ 10
OLD_DRV db 0,0
NEW_DRV db 0,0
FLAG1 equ LEFT_ALIGN+CHAR_FIELD_ASCIIZ
;******************************************************************************
; VALUES FOR THE MSG_DESC CONTROL BLOCK
ONE_SUBS EQU 1 ;ONE VARIABLE FIELD IN MESSAGE
TWO_SUBS EQU 2 ;TWO VARIABLE FIELDS IN MESSAGE
THREE_SUBS EQU 3 ;THREE VARIABLE FIELDS IN MESSAGE
CLASS_1 EQU EXT_ERR_CLASS ;CLASS 1 (DOS EXTENDED ERRORS)
CLASS_2 EQU PARSE_ERR_CLASS ;CLASS 2 (PARSE ERRORS)
CLASS_A EQU UTILITY_MSG_CLASS ;CLASS A TYPE MESSAGE
;THIS MESSAGE DESCRIPTOR CONTROL BLOCK IS GENERATED, ONE PER MESSAGE,
;TO DEFINE THE SEVERAL PARAMETERS THAT ARE EXPECTED TO BE PASSED IN
;CERTAIN REGISTERS WHEN THE SYSDISPMSG FUNCTION IS TO BE INVOKED.
MSG_DESC STRUC
MSG_NUM DW 0 ;MESSAGE NUMBER (TO AX)
MSG_HAND DW 0 ;HANDLE OF OUTPUT DEVICE (TO BX)
MSG_SUBLIST DW 0 ;POINTER TO SUBLIST (TO SI)
MSG_COUNT DW 0 ;SUBSTITUTION COUNT (TO CX)
MSG_CLASS DB 0 ;MESSAGE CLASS (IN HIGH BYTE, TO DH)
; LOW BYTE HAS 0 (FUNCTION "NO INPUT", TO DL)
MSG_DESC ENDS
; VALUES FOR THE SUBLIST CONTROL BLOCK
PC_ID_0 EQU 0 ;ID OF " - " TRAILER TO MESSAGE
PC_ID_1 EQU 1 ;ID OF PERCENT VARIABLE FIELD
PC_ID_2 EQU 2 ;ID OF PERCENT VARIABLE FIELD
PC_ID_3 EQU 3 ;ID OF PERCENT VARIABLE FIELD
MAX_0 EQU 0 ;MAXIMUM WIDTH OF STRING FIELD (0=NO LIMIT)
MIN_1 EQU 1 ;MINIMUM WIDTH OF STRING FIELD
;Message SUB-LIST
SUBLIST1 LABEL DWORD ;PARM LIST
;(Original %1: set to %2:)
DB 11 ;PARMLIST size
DB 0 ;reserved
DW OLD_DRV ;; ptr to data
SEG_1 DW ?
DB 1 ;; n of %n
DB FLAG1 ;; data type
DB max_0 ;;max width
DB min_1 ;;min width
DB PAD_CHAR ;;char defined to be space
DRV_LETS LABEL WORD
;Message SUB-LIST2
SUBLIST2 LABEL DWORD ;PARM LIST
;(File not found - 'PATH_SPEC')
DB 11 ;PARMLIST size
DB 0 ;reserved
DW NEW_DRV ;; ptr to data - offset
SEG_2 DW ? ;; ptr to data
DB 2 ;; n of %n
DB FLAG1 ;; data type
DB max_0 ;;max width
DB min_1 ;;min width
DB PAD_CHAR ;;char defined to be space


View File

@ -0,0 +1,141 @@
PAGE ,132 ;
TITLE ASSPARM.SAL - ASSIGN SYSTEM COMMAND LINE PARSER
;****************** START OF SPECIFICATIONS *****************************
; MODULE NAME: ASSGPARM.SAL
;
; DESCRIPTIVE NAME: Include the DOS system PARSER in the SEGMENT
; configuration expected by the modules of ASSIGN.
;
;FUNCTION: The common code of the DOS command line PARSER is optimized by
; the setting of certain switches that cause the conditional
; assembly of only the required portions of the common PARSER.
; The segment registers are ASSUMED according to the type .EXE.
;
; ENTRY POINT: SYSPARSE, near
;
; INPUT:
; ES - has seg id of the SEGMENT
; that contains the input control blocks,
; defined below.
;
; DI - offset into ES of the PARMS INPUT BLOCK
;
; DS - has seg id of the SEGMENT
; that contains the DOS input COMMAND
; string, which is originally presented at 81h
; in the PSP.
;
; SI - offset into DS of the text of the DOS input COMMAND string
; as originally presented at 81H in the PSP.
;
; DX - zero
;
; CX - ordinal value, intially zero, updated on each subsequent call
; to the value returned in CX on the previous call.
;
; CS - points to the segment containing the
; INCLUDE PARSE.SAL statement
;
; DS - also points to the segment containing the INCLUDE
; PARSE.SAL statement.
;
; EXIT-NORMAL: Output registers:
; AX - return code:
; RC_No_Error equ 0 ; No error
; RC_EOL equ -1 ; End of command line
;
; DX - Offset into ES of the selected RESULT BLOCK.
; BL - terminated delimiter code
; CX - new operand ordinal
; SI - set past scanned operand
;
; EXIT-ERROR: Output registers:
; AX - return code:
; RC_Too_Many equ 1 ; Too many operands
; RC_Op_Missing equ 2 ; Required operand missing
; RC_Not_In_SW equ 3 ; Not in switch list provided
; RC_Not_In_Key equ 4 ; Not in keyword list provided
; RC_Out_Of_Range equ 6 ; Out of range specified
; RC_Not_In_Val equ 7 ; Not in value list provided
; RC_Not_In_Str equ 8 ; Not in string list provided
; RC_Syntax equ 9 ; Syntax error
;
; INTERNAL REFERENCES:
; ROUTINES: SYSPARSE:near (INCLUDEd in PARSE.SAL)
;
; DATA AREAS: none
;
; EXTERNAL REFERENCES:
; ROUTINES: none
;
; DATA AREAS: control blocks pointed to by input registers.
;
; NOTES:
; This module should be processed with the ASMUT preprocessor
; with the re-alignment not requested, as:
;
; SALUT ASSPARM,NUL;
;
; To assemble these modules, the sequential
; ordering of segments may be used.
;
; For LINK instructions, refer to the PROLOG of the main module,
; ASSIGN.SAL
;
; REVISION HISTORY: A000 Version 4.00: add PARSER, System Message Handler,
;
; COPYRIGHT: "Microsoft DOS ASSIGN Utility"
; "Version 4.00 (C)Copyright 1988 Microsoft Corp"
; "Licensed Material - Program Property of Microsoft "
;
;****************** END OF SPECIFICATIONS *****************************
IF1
%OUT COMPONENT=ASSIGN, MODULE=ASSPARM.SAL...
ENDIF
; = = = = = = = = = = = =
HEADER <MACRO DEFINITION>
; = = = = = = = = = = = =
HEADER MACRO TEXT
.XLIST
SUBTTL TEXT
.LIST
PAGE
ENDM
; = = = = = = = = = = = =
HEADER <SYSPARSE - SYSTEM COMMAND LINE PARSER> ; ;AN000;
CODE SEGMENT PARA PUBLIC ; ;AN000;
ASSUME CS:CODE,DS:CODE,ES:CODE,SS:CODE ; ;AN000;
PUBLIC SYSPARSE ;SUBROUTINE ENTRY POINT ;AN000;
CAPSW EQU 1 ;SUPPORT FILENAME TBL CAPS
FARSW EQU 0 ;PARSER CALL NEAR
FILESW EQU 0 ;CHECK FOR FILESPEC
DATESW EQU 0 ;SUPPRESS DATE CHECKING
TIMESW EQU 0 ;SUPPRESS TIME CHECKING
CMPXSW EQU 0 ;SUPPRESS CHECKING COMPLEX LIST
NUMSW EQU 0 ;SUPPRESS CHECKING NUMERIC VALUE
KEYSW EQU 0 ;SUPPRESS KEYWORD SUPPORT
VAL1SW EQU 0 ;SUPPRESS SUPPORT OF VALUE DEFINITION 1
VAL2SW EQU 0 ;SUPPRESS SUPPORT OF VALUE DEFINITION 2
VAL3SW EQU 1 ;SUPPORT OF VALUE DEFINITION 3
DRVSW EQU 0 ;SUPPORT OF DRIVE ONLY FORMAT
QUSSW EQU 0 ;SUPPRESS SUPPORT OF QUOTED STRING FORMAT
IF1 ; ;AN000;
%OUT COMPONENT=ASSIGN, SUBCOMPONENT=PARSE, MODULE=PARSE.ASM...
%OUT COMPONENT=ASSIGN, SUBCOMPONENT=PARSE, MODULE=PSDATA.INC...
ENDIF ; ;AN000;
;PARSE WORK AREA & EQUATES
.xlist
INCLUDE PARSE.ASM
.list
CODE ENDS
END


View File

@ -0,0 +1,242 @@
ASS_PARMS label dword
dw ASS_PARMSX
db 1 ;list of extra delimiters
db 3 ;0 length
db ";+="
ASS_PARMSX label byte
db 0,1
;Min 0 - no drive or switch specified
;Max 1 - maximal allowance of drive letters
;repeats
dw ASS_POS1 ;positional ctl ptr
db 1 ;# of switches
dw ASS_SW1 ;switch ptr
ASS_POS1 label word
dw 2010h ;Simple string,
;ignore colon, &
;repeat
;allowed
dw 0002h ;Cap result by
; character table
dw Result_Val ;tbl
dw Res_CTLVAL ;value list
db 0 ;no switch or
;keyword synonyms
db 0 ;alternative keyword
ASS_SW1 label word
dw 0 ;20010h ;Simple string,
;ignore colon & repeat
;allowed
dw 0002h ;Cap result by
;character table
dw Result_Valsw ;tbl
dw 0 ; ;value list
db 2 ;switch or
;keyword synonyms
SW_Syn1 db "/STATUS",0 ;alternate keyword
SW_Syn2 db "/STA",0 ;alternate keyword
Res_CTLVAL label word
db 3 ;List of simple strings
db 0 ;not in range defn.
db 0 ;not in numeric defn.
db 26 ;# of strings defined
db "A" ;item tag
;value returned
dw DRVA_PTR ;string ptr
db "B" ;item tag
;value returned
dw DRVB_PTR ;string ptr
db "C" ;item tag
;value returned
dw DRVC_PTR ;string ptr
db "D" ;item tag
;value returned
dw DRVD_PTR ;string ptr
db "E" ;item tag
;value returned
dw DRVE_PTR ;string ptr
db "F" ;item tag
;value returned
dw DRVF_PTR ;string ptr
db "G" ;item tag
;value returned
dw DRVG_PTR ;string ptr
db "H" ;item tag
;value returned
dw DRVH_PTR ;string ptr
db "I" ;item tag
;value returned
dw DRVI_PTR ;string ptr
db "J" ;item tag
;value returned
dw DRVJ_PTR ;string ptr
db "K" ;item tag
;value returned
dw DRVK_PTR ;string ptr
db "L" ;item tag
;value returned
dw DRVL_PTR ;string ptr
db "M" ;item tag
;value returned
dw DRVM_PTR ;string ptr
db "N" ;item tag
;value returned
dw DRVN_PTR ;string ptr
db "O" ;item tag
;value returned
dw DRVO_PTR ;string ptr
db "P" ;item tag
;value returned
dw DRVP_PTR ;string ptr
db "Q" ;item tag
;value returned
dw DRVQ_PTR ;string ptr
db "R" ;item tag
;value returned
dw DRVR_PTR ;string ptr
db "S" ;item tag
;value returned
dw DRVS_PTR ;string ptr
db "T" ;item tag
;value returned
dw DRVT_PTR ;string ptr
db "U" ;item tag
;value returned
dw DRVU_PTR ;string ptr
db "V" ;item tag
;value returned
dw DRVV_PTR ;string ptr
db "W" ;item tag
;value returned
dw DRVW_PTR ;string ptr
db "X" ;item tag
;value returned
dw DRVX_PTR ;string ptr
db "Y" ;item tag
;value returned
dw DRVY_PTR ;string ptr
db "Z" ;item tag
;value returned
dw DRVZ_PTR ;string ptr
DRVA_PTR LABEL word
db "A",0
DRVB_PTR LABEL word
db "B",0
DRVC_PTR LABEL word
db "C",0
DRVD_PTR LABEL word
db "D",0
DRVE_PTR LABEL word
db "E",0
DRVF_PTR LABEL word
db "F",0
DRVG_PTR LABEL word
db "G",0
DRVH_PTR LABEL word
db "H",0
DRVI_PTR LABEL word
db "I",0
DRVJ_PTR LABEL word
db "J",0
DRVK_PTR LABEL word
db "K",0
DRVL_PTR LABEL word
db "L",0
DRVM_PTR LABEL word
db "M",0
DRVN_PTR LABEL word
db "N",0
DRVO_PTR LABEL word
db "O",0
DRVP_PTR LABEL word
db "P",0
DRVQ_PTR LABEL word
db "Q",0
DRVR_PTR LABEL word
db "R",0
DRVS_PTR LABEL word
db "S",0
DRVT_PTR LABEL word
db "T",0
DRVU_PTR LABEL word
db "U",0
DRVV_PTR LABEL word
db "V",0
DRVW_PTR LABEL word
db "W",0
DRVX_PTR LABEL word
db "X",0
DRVY_PTR LABEL word
db "Y",0
DRVZ_PTR LABEL word
db "Z",0
RESULT_VAL label word
RESULT_VALSW label word
RES_TYPE db 0 ;Result_type
RES_ITAG db 0 ;Matched
;item tag
RES_SYN dw 0 ;synonym
;returned
RES_SOFF dw 0 ;drive type
;or beginning
;of string
;may be string
RES_SEG dw 0 ;string offset
;if type specified
;=========================================================================
; Sublist Definition Area
;=========================================================================
Parse_Sublist label word
db Sublist_Length ;sublist length ;an002; dms;
db Reserved ;reserved for future growth ;an002; dms;
Parse_Sub_Off dw ? ;offset of replaceable parm ;an002; dms;
Parse_Sub_Seg dw ? ;segment of replaceable parm ;an002; dms;
db 0 ;replaceable parm 0 ;an002; dms;
db Left_Align+Char_Field_ASCIIZ ; ;an002; dms;
db 40 ;max width ;an002; dms;
db 1 ;min width ;an002; dms;
db 20h ;blank fill ;an002; dms;

View File

@ -0,0 +1,9 @@
:util ASSIGN
:class 2 ;parse errors:
:class A ;"Original %1: set to %2:"
:use 1 COMMON1 ;MSG 1 is always
;"Incorrect DOS version"
:def 2 "Original %1: set to %2:",cr,lf
:end


View File

@ -0,0 +1,43 @@
#************************** makefile for cmd\assign ***************************
msg =..\..\messages
dos =..\..\dos
inc =..\..\inc
hinc =..\..\h
#
####################### dependencies begin here. #########################
#
all: assign.com
assign.ctl: assign.skl \
$(msg)\$(COUNTRY).msg \
makefile
assgparm.obj: assgparm.asm \
$(inc)\psdata.inc \
$(inc)\parse.asm \
makefile
assgmain.obj: assgmain.asm \
$(inc)\dosmac.inc \
$(inc)\sysvar.inc \
$(inc)\mult.inc \
$(inc)\pdb.inc \
$(inc)\syscall.inc \
$(inc)\msgserv.asm \
$(inc)\sysmsg.inc \
assgparm.inc \
assgmsg.inc \
assign.ctl \
assign.cla \
assign.cl1 \
assign.cl2 \
$(inc)\curdir.inc \
makefile
assign.com: assgmain.obj assgparm.obj
link assgmain.obj+assgparm.obj,assign,,;
exe2bin assign.exe assign.com
del assign.exe

2685
v4.0/src/CMD/ATTRIB/ATTRIB.C Normal file

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,443 @@
/* Module ATTRIB.H */
/*ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ*/
/* All defines for attrib.c */
/*ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ*/
#define FALSE 0 /*;AN000;*/
#define TRUE !FALSE /*;AN000;*/
#ifndef BYTE
#define BYTE unsigned char /*;AN000;*/
#define WORD unsigned short /*;AN000;*/
#define DWORD unsigned long /*;AN000;*/
#endif
#define CARRY 0x0001 /*;AN000; carry flag */
#define YES 1 /*;AN000; Yes return from int 21h Y/N check */
#define NO 0 /*;AN000; NO return from int 21h Y/N check */
#define NUL 0x0 /*;AN000;*/
#define BLANK 0x20 /*;AN000;*/
#define TAB 0x09 /*;AN000;*/
#define CR 0x0d /*;AN000;*/
#define LF 0x0a /*;AN000;*/
/* Error_exit() parameter values */
#define ERR_EXTENDED 1 /*;AN000;*/
#define ERR_PARSE 2 /*;AN000;*/
/* standard file handles */
#define STDIN 0x00 /*;AN000; Standard Input device handle */
#define STDOUT 0x01 /*;AN000; Standard Output device handle */
#define STDERR 0x02 /*;AN000; Standard Error Output device handle */
#define STDAUX 0x03 /*;AN000; Standard Auxiliary device handle */
#define STDPRN 0x04 /*;AN000; Standard Printer device handle */
/* attribute byte defines */
#define AFILE 0x00 /*;AN000;*/
#define READONLY 0x01 /*;AN000;*/
#define HIDDEN 0x02 /*;AN000;*/
#define SYSTEM 0x04 /*;AN000;*/
#define LABEL 0x08 /*;AN000;*/
#define SUBDIR 0x10 /*;AN000;*/
#define ARCHIVE 0x20 /*;AN000;*/
/* extended attribute type defines */
#define EAISUNDEF 0 /*;AN000; undefined type */
#define EAISLOGICAL 1 /*;AN000; logical (0 or 1) */
#define EAISBINARY 2 /*;AN000; binary integer */
#define EAISASCII 3 /*;AN000; ASCII type */
#define EAISDATE 4 /*;AN000; DOS file date format */
#define EAISTIME 5 /*;AN000; DOS file time format */
#define EANAMES 6 /*;AN000; ext attr names ASCII */
/* extended attribute flag defines */
#define EASYSTEM 0x8000 /*;AN000; EA is system defined */
#define EAREADONLY 0x4000 /*;AN000; EA is read only */
#define EAHIDDEN 0x2000 /*;AN000; EA is hidden */
#define EACREATEONLY 0x1000 /*;AN000; EA is setable only at create time */
/* extended attribute failure return code defines */
#define EARCNOERROR 0 /*;AN000; no error */
#define EARCNOTFOUND 1 /*;AN000; name not found */
#define EARCNOSPACE 2 /*;AN000; no space to hold name or value */
#define EARCNOTNOW 3 /*;AN000; name can't be set on this function */
#define EARCNOTEVER 4 /*;AN000; name can't be set */
#define EARCUNDEF 5 /*;AN000; name known to this FS but not supported */
#define EARCDEFBAD 6 /*;AN000; EA definition bad (TYPE,LENGTH, etc.) */
#define EARCACCESS 7 /*;AN000; EA access denied */
#define EARCVALBAD 8 /*;AN000; EA value not supported */
#define EARCUNKNOWN -1 /*;AN000; undetermined cause */
/* message retriever interface defines */
#define NOSUBPTR 0 /*;AN000; no sublist pointer */
#define NOSUBCNT 0 /*;AN000; 0 substitution count */
#define ONEPARM 1 /*;AN000; 1 substitution count */
#define TWOPARM 2 /*;AN000; 2 substitution count */
#define NOINPUT 0 /*;AN000; no user input */
#define INPUT 1 /*;AN000; ask user for Y/N input */
/* misc. defines */
#define A_FILESIZE 1 /* id of special attribute: filesize */
#define A_DATE 2 /* id of special attribute: date */
#define A_TIME 3 /* id of special attribute: time */
#define MAX_ATTR_SIZE 160 /*;AN000; max ext attribute buffer size */
#define MAX_KEYWORD 128 /*;AN000; max size of extended attribute keyword */
#define MAX_SPL 3 /*;AN000; max number of special attributes */
#define ATTR_SIZE 7 /*;AN000; size in bytes of attr struct */
#define NAME_SIZE 4 /*;AN000; size in bytes of name struct */
#define NOERROR 0 /*;AN000;*/
#define NOMOREFILES 18 /*;AN000;*/
#define FILENOTFOUND 2 /*;AN000;*/
#define GET_DATE 1 /*;AN000;*/
#define GET_TIME 2 /*;AN000;*/
#define INACTIVE 0x7fff /*;AN000;*/
/*ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ*/
/* All structures defined for attrib.c */
/*ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ*/
struct p_null { /*;AN000; a null value list for parser */
unsigned char null; /*;AN000;*/
}; /*;AN000;*/
struct query_list { /*;AN000; Generic attribute overlay structure */
WORD ql_num;
BYTE ql_type; /*;AN000; EA type */
WORD ql_flags; /*;AN000; EA flags */
BYTE ql_name_len; /*;AN000; name length */
char ql_name[MAX_KEYWORD]; /*;AN000; name */
}; /*;AN000;*/
struct name_list { /*;AN000; Generic attribute overlay structure */
BYTE nl_type; /*;AN000; EA type */
WORD nl_flags; /*;AN000; EA flags */
BYTE nl_name_len; /*;AN000; name length */
char nl_name[MAX_KEYWORD]; /*;AN000; name */
}; /*;AN000;*/
struct attr_list { /*;AN000; Generic attribute overlay structure */
BYTE at_type; /*;AN000; EA type */
WORD at_flags; /*;AN000; EA flags */
BYTE at_rc; /*;AN000; EA return code */
BYTE at_name_len; /*;AN000; name length */
WORD at_value_len; /*;AN000; value length */
char at_name[MAX_KEYWORD]; /*;AN000; name */
}; /*;AN000;*/
struct parm_list { /*;AN000; Parm list for extended open DOS call */
DWORD pm_list; /*;AN000; extended attr. list */
WORD pm_num_parms; /*;AN000; number of parameters */
BYTE pm_id; /*;AN000; id */
WORD pm_iomode; /*;AN000; iomode */
}; /*;AN000;*/
struct spl_list { /*;AN000;*/
char name[MAX_KEYWORD]; /*;AN000;*/
WORD id; /*;AN000;*/
}; /*;AN000;*/
struct bin_struct { /*;AN000;*/
BYTE length; /*;AN000;*/
DWORD dword; /*;AN000;*/
}; /*;AN000;*/
union eav_union { /*;AN000;*/
WORD ea_undef; /*;AN000;*/
BYTE ea_logical; /*;AN000;*/
struct bin_struct ea_bin; /*;AN000;*/
char ea_ascii[129]; /*;AN000;*/
DWORD ea_time; /*;AN000;*/
DWORD ea_date; /*;AN000;*/
}; /*;AN000;*/
/*ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ*/
/* All global variables for attrib.c */
/*ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ*/
struct spl_list specials[MAX_SPL] = { /*;AN000;*/
"FILESIZE", A_FILESIZE, /*;AN000;*/
"DATE", A_DATE, /*;AN000;*/
"TIME", A_TIME }; /*;AN000;*/
/* parser structure variables */
union eav_union ext_attr_value; /*;AN000; result value union */
struct p_result_blk pos1_buff; /*;AN000; result buffer for -+A,-+R */
struct p_result_blk pos2_buff; /*;AN000; result buffer for -+A,-+R */
struct p_result_blk pos3_buff; /*;AN000; result buffer for filespec */
struct p_result_blk pos4_buff; /*;AN000; result buffer for -+A,-+R */
struct p_result_blk pos5_buff; /*;AN000; result buffer for -+A,-+R */
struct p_result_blk pos6_buff; /*;AN000; result buffer for id */
struct p_result_blk pos6b_buff; /*;AN000; result buffer for id */
struct p_result_blk sw_buff; /*;AN000; result buffer for /S */
char nullword[] = " "; /*;AN000; used when no word attribute */
char nulldword[] = " "; /*;AN000; used when no double word attribute */
char nulldate[] = " "; /*;AN000; used when no date attribute */
char nulltime[] = " "; /*;AN000; used when no time attribute */
char plusa[] = "+A"; /*;AN000; strings for match */
char minusa[] = "-A"; /*;AN000;*/
char plusr[] = "+R"; /*;AN000;*/
char minusr[] = "-R"; /*;AN000;*/
struct p_null noval = /*;AN000; structure for no value list */
{ 0 }; /*;AN000;*/
struct ps_valist_blk vals1 = /*;AN000; +A-A+R-R value list */
{ p_nval_string, /*;AN000; string value list type */
0, /*;AN000; number of ranges */
0, /*;AN000; number of numbers */
4, /*;AN000; number of strings */
0x20, /*;AN000; item tag */
(WORD)plusa, /*;AN000; address of string */
0x20, /*;AN000; item tag */
(WORD)minusa, /*;AN000; address of string */
0x01, /*;AN000; item tag */
(WORD)plusr, /*;AN000; address of string */
0x01, /*;AN000; item tag */
(WORD)minusr }; /*;AN000; address of string */
struct p_control_blk p_con1 = /*;AN000; describes +-A or +-R */
{ 0x2001, /*;AN000; Simple string,optional */
0x0002, /*;AN000; Cap result by char table */
(WORD)&pos1_buff, /*;AN000;*/
(WORD)&vals1, /*;AN000;*/
0, /*;AN000;*/
0 }; /*;AN000;*/
struct p_control_blk p_con2 = /*;AN000; describes +-A or +-R (2nd occurrance) */
{ 0x2001, /*;AN000; Simple string,optional */
0x0002, /*;AN000; Cap result by char table */
(WORD)&pos2_buff, /*;AN000;*/
(WORD)&vals1, /*;AN000;*/
0, /*;AN000;*/
0 }; /*;AN000;*/
struct p_control_blk p_con3 = /*;AN000; describes filespec */
{ 0x0200, /*;AN000; File spec required */
0x0001, /*;AN000; Cap result by file table */
(WORD)&pos3_buff, /*;AN000;*/
(WORD)&noval, /*;AN000;*/
0, /*;AN000;*/
0 }; /*;AN000;*/
struct p_control_blk p_con4 = /*;AN000; describes +-A or +-R */
{ 0x2001, /*;AN000; Simple string,optional */
0x0002, /*;AN000; Cap result by char table */
(WORD)&pos4_buff, /*;AN000;*/
(WORD)&vals1, /*;AN000;*/
0, /*;AN000;*/
0 }; /*;AN000;*/
struct p_control_blk p_con5 = /*;AN000; describes +-A or +-R (2nd occurrance) */
{ 0x2001, /*;AN000; Simple string,optional */
0x0002, /*;AN000; Cap result by char table */
(WORD)&pos5_buff, /*;AN000;*/
(WORD)&vals1, /*;AN000;*/
0, /*;AN000;*/
0 }; /*;AN000;*/
struct p_control_blk p_con6 = /*;AN000; describes id */
{ 0x2001, /*;AN000; Simple string,optional */
0x0002, /*;AN000; Cap result by char table */
(WORD)&pos6_buff, /*;AN000;*/
(WORD)&noval, /*;AN000;*/
0, /*;AN000;*/
0 }; /*;AN000;*/
struct p_control_blk p_con6a = /*;AN000; describes id */
{ 0x2000, /*;AN000; Simple string */
0x0002, /*;AN000; Cap result by char table */
(WORD)&pos6_buff, /*;AN000;*/
(WORD)&noval, /*;AN000;*/
0, /*;AN000;*/
0 }; /*;AN000;*/
struct p_control_blk p_con6b = /*;AN000; describes id */
{ 0xe481, /*;AN000; Quoted string */
0x0002, /*;AN000;*/
(WORD)&pos6b_buff, /*;AN000;*/
(WORD)&noval, /*;AN000;*/
0, /*;AN000;*/
0 }; /*;AN000;*/
struct p_control_blk p_swi1 = /*;AN000; Switch control block */
{ 0x0001, /*;AN000; Optional (switch) */
0x0002, /*;AN000; Cap result by char table */
(WORD)&sw_buff, /*;AN000;*/
(WORD)&noval, /*;AN000;*/
1, /*;AN000; one switch allowed */
"/S" }; /*;AN000; /S */
struct p_parmsx p_px1 = /*;AN000; Parser Control definition for Parm Block 1 */
{ 1, /*;AN000; positionals */
6, /*;AN000;*/
&p_con1, /*;AN000;*/
&p_con2, /*;AN000;*/
&p_con3, /*;AN000;*/
&p_con4, /*;AN000;*/
&p_con5, /*;AN000;*/
&p_con6, /*;AN000;*/
1, /*;AN000; switches */
&p_swi1, /*;AN000;*/
0, /*;AN000; keywords*/
0, /*;AN000;*/
0, /*;AN000;*/
0 }; /*;AN000;*/
struct p_parms p_p1 = /*;AN000; Parms block for line */
{ &p_px1, /*;AN000; Address of extended parm list */
0, /*;AN000;*/
0, /*;AN000;*/
0 }; /*;AN000;*/
struct p_parmsx p_px2 = /*;AN000; Parser Control definition for Parm Block 1 */
{ 1, /*;AN000; positionals */
2, /*;AN000;*/
&p_con6a, /*;AN000;*/
&p_con6b, /*;AN000;*/
0, /*;AN000;*/
0, /*;AN000;*/
0, /*;AN000;*/
0, /*;AN000;*/
1, /*;AN000; switches */
&p_swi1, /*;AN000;*/
0, /*;AN000; keywords*/
0, /*;AN000;*/
0, /*;AN000;*/
0 }; /*;AN000;*/
struct p_parms p_p2 = /*;AN000; Parms block for line */
{ &p_px2, /*;AN000; Address of extended parm list */
1, /*;AN000;*/
1, /*;AN000;*/
"=" }; /*;AN000;*/
/* extended open structure variables */
struct parm_list plist = /*;AN000; Extended open parm list */
{ -1, /*;AN000; ptr to attr. list */
1, /*;AN000; number of parms */
6, /*;AN000; id */
2 }; /*;AN000; iomode */
/* messgages */
struct m_sublist msg_num = /*;AN000; describes substitutions */
{ 72, /*;AN000; for parm one of message */
0, /*;AN000; */
0, /*;AN000; */
0, /*;AN000; */
1, /*;AN000; */
sf_unsbin2d | sf_right, /*;AN000; unsigned binary to decimal*/
9, /*;AN000; */
9, /*;AN000; */
0 }; /*;AN000; */
struct m_sublist msg_str2 = /*;AN000; describes substitutions */
{ 60, /*;AN000; for parm one of message */
0, /*;AN000; */
0, /*;AN000; */
0, /*;AN000; */
1, /*;AN000; */
sf_left | sf_char | sf_asciiz, /*;AN000; string */
0, /*;AN000; null string */
0, /*;AN000; */
(BYTE)" " }; /*;AN000; */
struct m_sublist msg_dword = /*;AN000; describes substitutions */
{ 48, /*;AN000; for parm one of message */
0, /*;AN000; */
0, /*;AN000; */
0, /*;AN000; */
1, /*;AN000; */
sf_unsbin2d | sf_dword | sf_right, /*;AN000; unsigned binary to decimal*/
10, /*;AN000; */
9, /*;AN000; */
0 }; /*;AN000; */
struct m_sublist msg_date = /*;AN000; describes substitutions */
{ 36, /*;AN000; for parm one of message */
0, /*;AN000; */
0, /*;AN000; */
0, /*;AN000; */
1, /*;AN000; */
sf_date | sf_mdy2, /*;AN000; unsigned binary to decimal*/
9, /*;AN000; */
9, /*;AN000; */
0 }; /*;AN000; */
struct m_sublist msg_time = /*;AN000; describes substitutions */
{ 24, /*;AN000; for parm one of message */
0, /*;AN000; */
0, /*;AN000; */
0, /*;AN000; */
1, /*;AN000; */
sf_time12 | sf_hhmm | sf_right, /*;AN000; unsigned binary to decimal*/
9, /*;AN000; NN-NN-NNa (9 characters) */
9, /*;AN000; */
0 }; /*;AN000; */
struct m_sublist msg_str = /*;AN000; describes substitutions */
{ 12, /*;AN000; for parm one of message */
0, /*;AN000; */
0, /*;AN000; */
0, /*;AN000; */
1, /*;AN000; */
sf_left | sf_char | sf_asciiz, /*;AN000; string */
9, /*;AN000; null string */
9, /*;AN000; */
(BYTE)" " }; /*;AN000; */
struct m_sublist msg_str1 = /*;AN000; describes substitutions */
{ 12, /*;AN000; for parm two of message */
0, /*;AN000; */
0, /*;AN000; */
0, /*;AN000; */
2, /*;AN000; */
sf_left | sf_char | sf_asciiz, /*;AN000; string */
0, /*;AN000; null string */
0, /*;AN000; */
(BYTE)" " }; /*;AN000; */
struct m_sublist msg_error = /*;AN000; describes substitutions */
{ 12, /*;AN000; for extended error messages*/
0, /*;AN000; */
0, /*;AN000; */
0, /*;AN000; */
0, /*;AN000; */
sf_left | sf_char | sf_asciiz, /*;AN000; string */
0, /*;AN000; null string */
0, /*;AN000; */
(BYTE)" " }; /*;AN000; */
/* misc. variables */
union REGS inregs, /*;AN000; Registers */
outregs; /*;AN000;*/
struct SREGS segregs; /*;AN000; Segment registers */
DWORD old_int24_off; /*;AN000;*/
WORD descending; /*;AN000;*/
WORD append_x_status; /*;AN000;*/
WORD did_attrib_ok; /*;AN000;*/
WORD set_reg_attr, /*;AN000;*/
set_ext_attr; /*;AN000;*/
WORD do_reg_attr, /*;AN000;*/
do_ext_attr; /*;AN000;*/
BYTE far *DBCS_ptr; /*;AN000;*/
BYTE ext_attr_value_type; /*;AN000;*/
BYTE attr; /*;AN000;*/
BYTE bits[8] = { 0x80,0x40,0x20,0x10,0x08,0x04,0x02,0x01 }; /*;AN000;*/
BYTE pmask, /*;AN000;*/
mmask; /*;AN000;*/
char as[8] = { ' ',' ','A',' ',' ',' ',' ','R' }; /*;AN000;*/
char fix_es_reg[1]; /*;AN000;*/
char ext_attr[MAX_KEYWORD]; /*;AN000;*/
char error_file_name[256]; /*;AN005;*/
char fspec[256]; /*;AN000;*/
char file[256]; /*;AN000;*/
char str_on[3] = {"ON"}; /*;AN000;*/
char str_off[4] = {"OFF"}; /*;AN000;*/

View File

@ -0,0 +1,7 @@
attriba+
attrib+
_parse+
_msgret
attrib
nul;

View File

@ -0,0 +1,30 @@
:util ATTRIB ;utility name ;AN000;
:class 1 ;AN000;
:class 2 ;AN000;
:class A ;system messages ;AN000;
:use 1 COMMON1 ;"Incorrect DOS version" ;AN000;
:use 2 EXTEND8 ;"Insufficient memory" ;AN000;
:class B ;AN000;
:def 8 " %1" ;AN000;
:def 9 "%1 %2",CR,LF ;AN000;
:def 10 "%1",CR,LF,"%2",CR,LF ;AN000;
:def 11 "Code page mismatch - %1",CR,LF,"Are you sure (Y/N)?" ;AN000;
:def 12 "%1",CR,LF ;AN000;
:def 14 CR,LF ;AN000;
:def 15 "Invalid file type value",CR,LF ;AN000;
;;; Change these extended attribute error msgs back when adding ext. attr.
;;; function in DOS.
;;;:def 199 "Extended attribute error",CR,LF ;AN000;
;;;:def 201 "Extended attribute name not found",CR,LF ;AN000;
;;;:use 202 EXTEND8 ;"Insufficient memory" ;AN000;
;;;:def 204 "Extended attribute name can't be set",CR,LF ;AN000;
;;;:def 205 "Extended attribute name known to this filesystem but not supported",CR,LF ;AN000;
;;;:def 206 "Extended attribute type mismatch",CR,LF ;AN000;
;;;:def 208 "Extended attribute value not supported",CR,LF ;AN000;
:end ;AN000;

View File

@ -0,0 +1,480 @@
page ,132 ;
title New_C.C - DOS entry to the KWC's 'C' programs
;
; This module has been modified extensively for my personal
; use.
;
; name XCMAIN -- initiate execution of C program
;
; description This is the main module for a C program on the
; DOS implementation. It initializes the segment
; registers, sets up the stack, and calls the C main
; function _main with a pointer to the remainder of
; the command line.
;
; Also defined in this module is the exit entry point
; XCEXIT.
;
; $salut (4,12,18,41)
SETBLOCK EQU 4AH ;MODIFY ALLOCATED MEMORY BLOCKS
;ES = SEGMENT OF THE BLOCK
;BX = NEW REQUESTED BLOCK SIZE
; IN PARAGRAPHS
;OUTPUT: BX=MAX SIZE POSSIBLE IF CY SET
;AX = ERROR CODE IF CY SET
RET_CD_EXIT EQU 4CH ;EXIT TO DOS, PASSING RETURN CODE
;AL=RETURN CODE
RET_EXIT equ 4ch ;AN000; ;terminate
ABORT equ 2 ;AN000; ;if >=, retry
XABORT equ 1 ;AN000; ;errorlevel return in al
extrn _inmain:near ;AC000;
extrn _Reset_appendx:near ;AN000;
extrn _old_int24_off:dword ;AN000;
psp segment at 0 ;<--emk
psp_ret dw ? ;int 20h
psp_memsz dw ? ;memory size
org 2ch
psp_env dw ? ;segid of environment
org 80h
psp_parlen db ? ;length of DOS command line parms
psp_par db 127 dup(?) ;DOS command line parms
psp ends
page
;
; The following segment serves only to force "pgroup" lower in
; memory.
;
base segment PARA PUBLIC 'DATA'
db 00dh,00ah
db "----------\x0d\x0a"
db " DOS ATTRIB function \x0d\x0a"
db "--------------------\x0d\x0a"
db 00dh,00ah,01ah
base ends
;
; The data segment defines locations which contain the offsets
; of the base and top of the stack.
;
_data segment PARA public 'DATA'
irp name,<_top,_base,_cs,_ss,_psp,_env,_rax,_rbx,_rcx,_rdx,_rds,_rsi,_rbp,_res,_rdi>
public name
name dw 0
endm
_data ends
;
; The stack segment is included to prevent the warning from the
; linker, and also to define the base (lowest address) of the stack.
;
stack segment PARA stack 'data'
SBase dw 128 dup (?)
stack ends
null segment para public 'BEGDATA'
null ends
const segment word public 'CONST'
const ends
_bss segment word public 'BSS'
_bss ends
pgroup group base,_text
dgroup group null, _data, const, _bss, stack
page
;
; The main program must set up the initial segment registers
; and the stack pointer, and set up a far return to the DOS
; exit point at ES:0. The command line bytes from the program
; segment prefix are moved onto the stack, and a pointer to
; them supplied to the C main module _main (which calls main).
;
_text segment PARA public 'CODE'
public XCMAIN
assume cs:pgroup
assume ds:psp ;<--emk
assume es:psp ;<--emk
assume ss:stack ;<--emk
XCMAIN proc far
mov ax,dgroup
mov ds,ax ;initialize ds and ss
assume ds:dgroup
mov bx,psp_memsz ;total memory size (paragraphs)
sub bx,ax
test bx,0f000h
; $IF Z ;branch if more than or equal 64K bytes
JNZ $$IF1
mov cl,4
shl bx,cl ;highest available byte
; $ELSE
JMP SHORT $$EN1
$$IF1:
mov bx,0fff0h
; $ENDIF
$$EN1:
cli ; disable interrupts while changing stack <---kwc
mov ss,ax ; set ss <---kwc
mov sp,bx ; set stack pointer <---kwc
sti ;enable interrupts
assume ss:DGroup ;<--emk
mov _ss,ss
mov _cs,cs
mov _top,bx ;save top of stack
mov ax,offset DGroup:SBase
mov _base,ax ;store ptr to bottom of stack
; code added here to allow allocates and exec's in the c code
; we will have to calculate the size of the code that has been loaded
mov bx,sp ; bx = length of the stack
shr bx,1
shr bx,1
shr bx,1
shr bx,1 ; bx = number of paragraphs in stack,
add bx,1 ; (fudge factor!)<--emk ,was 10
mov ax,ss
add bx,ax ; bx = paragraph a little past the stack
mov ax,es ; ax = paragraph of the psp
sub bx,ax ; bx = number of paragraphs in code
mov ah,setblock
int 021h
; end of added code!
mov _psp,es ; save pointer to psp for setblock <---kwc
mov cl,psp_parlen ;get number of bytes <--emk
xor ch,ch ;cx = number of bytes of parms!
mov si,offset psp_par ;point to DOS command line parms <--emk
; more modified code, picking up argv[0] from the environment!
mov ds,psp_env ;set ds to segid of environment from es:psp
assume ds:nothing
mov _env,ds ;remember where environment is
mov si,0 ;clear index to step thru env
;The env has a set of keyword=operand, each one ending with a single null byte.
;At the end of the last one is a double null. We are looking for the end of
;all these keywords, by looking for the double null.
; $DO COMPLEX
JMP SHORT $$SD4
$$DO4:
inc si ;bump index to look at next byte in env
; $STRTDO
$$SD4:
cmp word ptr [si],0 ;is this a double null delimiter?
; $ENDDO E ;ifdouble null found, exit
JNE $$DO4
;At end of env is the double null and a word counter
add si,4 ;step over this double null delimiter
; and the following word counter
push si ;save pointer to next field in env
;This is the invocation statement, including the path name, even if not specified
;but supplied by PATH.
;continue stepping thru env looking for one more null byte, which indicates
;the end of the invocation command.
; $DO
$$DO7:
lodsb ;get a byte from env to al
cmp al,0 ;is this a null byte?
; $ENDDO E ;quit if null is found
JNE $$DO7
mov bx,si ; bx -> asciiz zero
pop si ; si -> first byte of agrv[0], the invocation command
sub bx,si ; bx = length of argv[0]
mov dx,bx ; (save for the copy later)
dec dx
add bx,cx ; add in the length of the rest of the parms
inc bx ; add one for the asciiz zero!
and bx,0fffeh ;force even number of bytes
add bx,2 ;adjust for possible rounding error
sub sp,bx ;allocate space on stack
mov di,sp ; (es:di) -> where we will put the stuff
push es
mov ax,ss
mov es,ax
xchg cx,dx ; length of argv[0] to copy, save length of parms
rep movsb ; (ds:si) already point to argv[0]
pop es
mov ss:byte ptr [di],' ' ;store trailing blank!
inc di
mov _rdi,di ;AN000; save start of command parms
xchg cx,dx ; restore length of parms
; $IF NCXZ ;if some bytes to move,
JCXZ $$IF9
mov si,offset psp_par ;point to DOS command line parms in psp
; $DO
$$DO10:
mov al,es:[si] ;move bytes to stack
mov ss:[di],al
inc si
inc di
; $ENDDO LOOP
LOOP $$DO10
; $ENDIF ;bytes to move?
$$IF9:
xor ax,ax
mov ss:[di],al ;store null byte
mov ax,ss
mov ds,ax ;es, ds, and ss are all equal
assume ds:DGroup
mov es,ax ;es, ds, and ss are all equal
assume es:DGroup
mov ax,_rdi ;AN000; restore offset of parms on stack
push ax ;ptr to command line
call _inmain ;AC000; call C main
mov ah,ret_cd_exit ;return to DOS
int 21h ;errorlevel ret code in al
XCMAIN endp
page
;
; name XCEXIT -- terminate execution of C program
;
; description This function terminates execution of the current
; program by returning to DOS. The error code
; argument normally supplied to XCEXIT is ignored
; in this implementation.
;
; input - al = binary return code for dos/ERRORLEVEL
;
assume cs:PGroup
assume ds:DGroup
assume es:DGroup
assume ss:DGroup
public xcexit
XCEXIT proc far
mov ah,ret_cd_exit ; <--- kwc
int 021h ; <--- kwc
XCEXIT endp
;--------------------------------------------------------------------------
PAGE
CENTER MACRO NAMELIST
PUSH BP ; SAVE CURRENT BP
MOV BP,SP ; POINT AT STACK WITH BP
WORKOFS = 0
IRP ANAME,<NAMELIST> ; FOR EACH WORKING VARIABLE
IFNB <&ANAME>
WORKOFS = WORKOFS-2 ; WE WILL ALLOCATE ONE
DOEQU &ANAME,%WORKOFS ; WORD ON THE STACK THAT
ENDIF
ENDM ; IS UNDER SS,BP
ADD SP,WORKOFS
ENDM
DOEQU MACRO NAME,VALUE
&NAME EQU &VALUE
ENDM
CEXIT MACRO VALUE
MOV SP,BP
POP BP
RET
ENDM
PAGE
; INPUT PARAMATERS PASSED ON STACK
PARMS STRUC
OLD_BP DW ? ; SAVED BP
RETADD DW ? ; RETURN ADDRESS
PARM_1 DW ?
PARM_2 DW ?
PARM_3 DW ?
PARM_4 DW ?
PARM_5 DW ?
PARM_6 DW ?
PARM_7 DW ?
PARM_8 DW ?
PARMS ENDS
SAVE_SS DW 0
SAVE_SP DW 0
PAGE
;************************************************************************
; ;
; Subroutine Name: ;
; getpspbyte ;
; ;
; Subroutine Function: ;
; get a byte from PSP ; ;
; ;
; Input: ;
; SS:[BP]+PARM1 = offset in PSP ;
; ;
; Output: ;
; AL = byte from PSP:offset ;
; ;
; C calling convention: ;
; char = getpspbyte(offset); ;
; ;
;************************************************************************
MOFFSET EQU PARM_1 ;AN000;
ASSUME CS:PGROUP ;AN000;
ASSUME DS:DGROUP ;AN000;
ASSUME ES:DGROUP ;AN000;
ASSUME SS:DGROUP ;AN000;
PUBLIC _GETPSPBYTE ;AN000;
_GETPSPBYTE PROC NEAR ;AN000;
CENTER ;AN000;
PUSH DS ;AN000;
MOV DS,_PSP ;AN000; get save PSP segment
MOV SI,[BP].MOFFSET ;AN000; get offset into PSP
LODSB ;AN000; get PSP byte
MOV AH,0 ;AN000; zero high byte
POP DS ;AN000;
CEXIT ;AN000;
_GETPSPBYTE ENDP
;************************************************************************
; ;
; Subroutine Name: ;
; putpspbyte ;
; ;
; Subroutine Function: ;
; put a byte into PSP ; ;
; ;
; Input: ;
; SS:[BP]+MVALUE = byte in AL ;
; SS:[BP]+MOFFSET = offset in PSP ;
; ;
; Output: ;
; none ;
; ;
; C calling convention: ;
; putpspbyte(offset,char); ;
; ;
;************************************************************************
MVALUE EQU PARM_2 ;AN000;
MOFFSET EQU PARM_1 ;AN000;
ASSUME CS:PGROUP ;AN000;
ASSUME DS:DGROUP ;AN000;
ASSUME ES:DGROUP ;AN000;
ASSUME SS:DGROUP ;AN000;
PUBLIC _PUTPSPBYTE ;AN000;
_PUTPSPBYTE PROC NEAR ;AN000;
CENTER ;AN000;
PUSH ES ;AN000;
MOV AX,[BP].MVALUE ;AN000; get byte to store in PSP
MOV ES,_PSP ;AN000; get saved PSP segment
MOV DI,[BP].MOFFSET ;AN000; get offset in PSP
STOSB ;AN000; store the byte
POP ES ;AN000;
CEXIT ;AN000;
_PUTPSPBYTE ENDP
;-------------------------------------------------------------------
;
; MODULE: crit_err_handler()
;
; PURPOSE: Supplies assembler exit routines for
; critical error situations
;
; CALLING FORMAT:
; crit_err_handler;
;-------------------------------------------------------------------
public _crit_err_handler ;AN000;
public vector ;AN000;
vector dd 0 ;AN000;
; ;AN000;
_crit_err_handler proc near ;AN000;
pushf ;AN000;
push ax ; save registers ;AN000;
push ds ;AN000;
mov ax,dgroup ;get C data segment ;AN000;
mov ds,ax ;AN000;
mov ax,word ptr ds:_old_int24_off ;get int24 offset ;AN000;
mov word ptr cs:vector,ax ;AN000;
mov ax,word ptr ds:_old_int24_off+2 ;get int24 segment ;AN000;
mov word ptr cs:vector+2,ax ;AN000;
pop ds ;restore registers ;AN000;
pop ax ;AN000;
; ;AN000;
call dword ptr cs:vector ; invoke DOS err hndlr ;AN000;
cmp al,ABORT ; what was the user's response ;AN000;
jnge retry ; ;AN000;
; ;AN000;
mov ax,dgroup ;get C data segment ;AN000;
mov ds,ax ;AN000;
mov es,ax ;AN000;
call _Reset_appendx ; restore user's orig append/x ;AN000;
; ;AN000;
mov ax,(RET_EXIT shl 8)+XABORT ; return to DOS w/criterr error ;AN000;
int 21h ; ;AN000;
retry: ;AN000;
iret ;AN000;
; ;AN000;
_crit_err_handler endp ;AN000;
_text ends ;AN000;
end XCMAIN ;AN000;


View File

@ -0,0 +1,46 @@
#************************** makefile for cmd\append ***************************
msg =..\..\messages
dos =..\..\dos
inc =..\..\inc
hinc =..\..\h
#
####################### dependencies begin here. #########################
#
all: attrib.exe
attrib.ctl: attrib.skl \
$(msg)\$(COUNTRY).msg \
makefile
_parse.obj: _parse.asm \
$(inc)\parse.asm \
$(inc)\psdata.inc
_msgret.obj: _msgret.asm \
$(inc)\msgserv.asm \
$(inc)\sysmsg.inc \
$(inc)\copyrigh.inc \
attrib.skl \
attrib.ctl \
attrib.cl1 \
attrib.cl2 \
attrib.cla \
attrib.clb
attriba.obj: attriba.asm
attrib.obj: attrib.c \
attrib.h \
parse.h \
msgret.h \
makefile
attrib.exe: attrib.obj \
attriba.obj \
_parse.obj \
_msgret.obj \
attrib.lnk
link @attrib.lnk

View File

@ -0,0 +1,60 @@
/*  */
/*----------------------------------------------------------------------+
| |
| This file contains the structures and defines that are needed to use |
| the message retriever from a C program. |
| |
| |
| Date: 6-19-87 |
| |
+----------------------------------------------------------------------*/
#define utility_msg_class 0xff /*;AN000; Utility message type */
#define exterr_msg_class 0x01 /*;AN000;*/
/* Sublist Flag Values */
/* Alignment Indicator */
#define sf_left 0x00 /*;AN000; left align */
#define sf_right 0x80 /*;AN000; right align */
/* Field Type */
#define sf_char 0x00 /*;AN000; character */
#define sf_unsbin2d 0x01 /*;AN000; unsigned binary to decimal */
#define sf_sbin 0x02 /*;AN000; signed binary to decimal */
#define sf_unsbin2h 0x03 /*;AN000; unsigned binary to hex */
#define sf_date 0x04 /*;AN000; date */
#define sf_time12 0x05 /*;AN000; time 12-hour */
#define sf_time24 0x06 /*;AN000; time 24-hour */
/* Data Variable Size */
#define sf_ch 0x00 /*;AN000; single character */
#define sf_asciiz 0x10 /*;AN000; asciiz string */
#define sf_byte 0x10 /*;AN000; byte */
#define sf_word 0x20 /*;AN000; word */
#define sf_dword 0x30 /*;AN000; double word */
#define sf_mdy2 0x20 /*;AN000; month,day,year (2 digits) */
#define sf_mdy4 0x30 /*;AN000; month,day,year (4 digits) */
#define sf_hhmm 0x00 /*;AN000; hh:mm */
#define sf_hhmmss 0x10 /*;AN000; hh:mm:ss */
#define sf_hhmmsshh 0x20 /*;AN000; hh:mm:ss:hh */
struct m_sublist /*;AN000; */
{ /*;AN000; */
BYTE sub_size; /*;AN000; */
BYTE sub_res; /*;AN000; */
WORD sub_value; /*;AN000; */
WORD sub_value_seg; /*;AN000; */
BYTE sub_id; /*;AN000; */
BYTE sub_flags; /*;AN000; */
BYTE sub_max_width; /*;AN000; */
BYTE sub_min_width; /*;AN000; */
BYTE sub_pad_char; /*;AN000; */
}; /*;AN000; */

185
v4.0/src/CMD/ATTRIB/PARSE.H Normal file
View File

@ -0,0 +1,185 @@
/*  */
/*----------------------------------------------------------------------+
| |
| This file contains the structures and defines that are needed to use |
| the parser from a C program. |
| |
| |
| Date: 5-21-87 |
| |
+----------------------------------------------------------------------*/
#define BYTE unsigned char /*;AN000;*/
#define WORD unsigned short /*;AN000;*/
#define DWORD unsigned long /*;AN000;*/
#define p_len_parms 4 /* length of p_parms */ /*;AN000;*/
#define p_i_use_default 0 /* no extra stuff specified */ /*;AN000;*/
#define p_i_have_delim 1 /* extra delimiter specified */ /*;AN000;*/
#define p_i_have_eol 2 /* extra EOL specified */ /*;AN000;*/
struct p_parms /*;AN000;*/
{ /*;AN000;*/
struct p_parmsx *p_parmsx_address; /* address of p_parmsx */ /*;AN000;*/
BYTE p_num_extra; /* number of extra stuff */ /*;AN000;*/
BYTE p_len_extra_delim; /* length of extra delimiter */ /*;AN000;*/
char p_extra_delim[30]; /* extra delimiters */ /*;AN000;*/
}; /*;AN000;*/
struct p_parmsx /*;AN000;*/
{ /*;AN000;*/
BYTE p_minp; /* Minimum positional number */ /*;AN000;*/
BYTE p_maxp; /* Maximum positional number */ /*;AN000;*/
struct p_control_blk *p_control1; /* Address of the 1st CONTROL block */ /*;AN000;*/
struct p_control_blk *p_control2; /* Address of the 2nd CONTROL block */ /*;AN000;*/
struct p_control_blk *p_control3; /* Address of the 3nd CONTROL block */ /*;AN000;*/
struct p_control_blk *p_control4; /* Address of the 4th CONTROL block */ /*;AN000;*/
struct p_control_blk *p_control5; /* Address of the 3nd CONTROL block */ /*;AN000;*/
struct p_control_blk *p_control6; /* Address of the 4th CONTROL block */ /*;AN000;*/
BYTE p_maxs; /*;AN000;*/
struct p_control_blk *p_switch; /*;AN000;*/
BYTE p_maxk; /*;AN000;*/
struct p_control_blk *p_keyword1; /*;AN000;*/
struct p_control_blk *p_keyword2; /*;AN000;*/
struct p_control_blk *p_keyword3; /*;AN000;*/
}; /*;AN000;*/
struct p_control_blk /*;AN000;*/
{ /*;AN000;*/
WORD p_match_flag; /* Controls type matched */ /*;AN000;*/
WORD p_function_flag; /* Function should be taken */ /*;AN000;*/
WORD p_result_buf; /* Result buffer address */ /*;AN000;*/
WORD p_value_list; /* Value list address */ /*;AN000;*/
BYTE p_nid; /* # of keyword/SW synonyms */ /*;AN000;*/
char p_keyorsw[20]; /* keyword or sw */ /*;AN000;*/
}; /*;AN000;*/
/* Match_Flags */ /*;AN000;*/
#define p_num_val 0x8000 /* Numeric Value */ /*;AN000;*/
#define p_snum_val 0x4000 /* Signed numeric value */ /*;AN000;*/
#define p_simple_s 0x2000 /* Simple string */ /*;AN000;*/
#define p_date_s 0x1000 /* Date string */ /*;AN000;*/
#define p_time_s 0x0800 /* Time string */ /*;AN000;*/
#define p_cmpx_s 0x0400 /* Complex string */ /*;AN000;*/
#define p_file_spc 0x0200 /* File Spec */ /*;AN000;*/
#define p_drv_only 0x0100 /* Drive Only */ /*;AN000;*/
#define p_qu_string 0x0080 /* Quoted string */ /*;AN000;*/
#define p_ig_colon 0x0010 /* Ignore colon at end in match */ /*;AN000;*/
#define p_repeat 0x0002 /* Repeat allowed */ /*;AN000;*/
#define p_optional 0x0001 /* Optional */ /*;AN000;*/
/*----------------------------------------------------------------------+
| |
| Function flags |
| |
+----------------------------------------------------------------------*/
#define p_cap_file 0x0001 /* CAP result by file table */ /*;AN000;*/
#define p_cap_char 0x0002 /* CAP result by character table */ /*;AN000;*/
#define p_rm_colon 0x0010 /* Remove ":" at the end */ /*;AN000;*/
#define p_nval_none 0 /* no value list ID */ /*;AN000;*/
#define p_nval_range 1 /* range list ID */ /*;AN000;*/
#define p_nval_value 2 /* value list ID */ /*;AN000;*/
#define p_nval_string 3 /* string list ID */ /*;AN000;*/
#define p_len_range 9 /* Length of a range choice(two DD plus one DB) */ /*;AN000;*/
#define p_len_value 5 /* Length of a value choice(one DD plus one DB) */ /*;AN000;*/
#define p_len_string 3 /* Length of a string choice(one DW plus one DB) */ /*;AN000;*/
/*----------------------------------------------------------------------+
| |
| Result block structure |
| |
+----------------------------------------------------------------------*/
struct p_result_blk /*;AN000;*/
{ /*;AN000;*/
BYTE p_type; /* Type returned */ /*;AN000;*/
BYTE p_item_tag; /* Matched item tag */ /*;AN000;*/
WORD p_synonym_ptr; /* pointer to Synonym list returned */ /*;AN000;*/
WORD p_result_buff[2]; /* result value */ /*;AN000;*/
}; /*;AN000;*/
/*----------------------------------------------------------------------+
| |
| type |
| |
+----------------------------------------------------------------------*/
#define p_eol 0 /* End of line */ /*;AN000;*/
#define p_number 1 /* Number */ /*;AN000;*/
#define p_list_idx 2 /* List Index */ /*;AN000;*/
#define p_string 3 /* String */ /*;AN000;*/
#define p_complex 4 /* Complex */ /*;AN000;*/
#define p_file_spec 5 /* File Spec */ /*;AN000;*/
#define p_drive 6 /* Drive */ /*;AN000;*/
#define p_date_f 7 /* Date */ /*;AN000;*/
#define p_time_f 8 /* Time */ /*;AN000;*/
#define p_quoted_string 9 /* Quoted String */ /*;AN000;*/
#define p_no_tag 0x0FF /* No ITEM_TAG found */ /*;AN000;*/
/*----------------------------------------------------------------------+
| |
| following return code will be returned in the AX register. |
| |
+----------------------------------------------------------------------*/
#define p_no_error 0 /* No error */ /*;AN000;*/
#define p_too_many 1 /* Too many operands */ /*;AN000;*/
#define p_op_missing 2 /* Required operand missing */ /*;AN000;*/
#define p_not_in_sw 3 /* Not in switch list provided */ /*;AN000;*/
#define p_not_in_key 4 /* Not in keyword list provided */ /*;AN000;*/
#define p_out_of_range 6 /* Out of range specified */ /*;AN000;*/
#define p_not_in_val 7 /* Not in value list provided */ /*;AN000;*/
#define p_not_in_str 8 /* Not in string list provided */ /*;AN000;*/
#define p_syntax 9 /* Syntax error */ /*;AN000;*/
#define p_rc_eol 0x0ffff /* End of command line */ /*;AN000;*/
/*----------------------------------------------------------------------+
| |
| String Value List Block Structure |
| |
+----------------------------------------------------------------------*/
struct ps_valist_blk /*;AN000;*/
{ /*;AN000;*/
BYTE ps_val; /* Value type */ /*;AN000;*/
BYTE ps_nrng; /* Number of ranges */ /*;AN000;*/
BYTE ps_nnval; /* Number of numbers */ /*;AN000;*/
BYTE ps_nstrval; /* Number of strings */ /*;AN000;*/
BYTE ps_item_tag1; /* Matched item tag */ /*;AN000;*/
WORD ps_strings1; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag2; /* Matched item tag */ /*;AN000;*/
WORD ps_strings2; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag3; /* Matched item tag */ /*;AN000;*/
WORD ps_strings3; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag4; /* Matched item tag */ /*;AN000;*/
WORD ps_strings4; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag5; /* Matched item tag */ /*;AN000;*/
WORD ps_strings5; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag6; /* Matched item tag */ /*;AN000;*/
WORD ps_strings6; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag7; /* Matched item tag */ /*;AN000;*/
WORD ps_strings7; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag8; /* Matched item tag */ /*;AN000;*/
WORD ps_strings8; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag9; /* Matched item tag */ /*;AN000;*/
WORD ps_strings9; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag10; /* Matched item tag */ /*;AN000;*/
WORD ps_strings10; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag11; /* Matched item tag */ /*;AN000;*/
WORD ps_strings11; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag12; /* Matched item tag */ /*;AN000;*/
WORD ps_strings12; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag13; /* Matched item tag */ /*;AN000;*/
WORD ps_strings13; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag14; /* Matched item tag */ /*;AN000;*/
WORD ps_strings14; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag15; /* Matched item tag */ /*;AN000;*/
WORD ps_strings15; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag16; /* Matched item tag */ /*;AN000;*/
WORD ps_strings16; /* Address of strings */ /*;AN000;*/
BYTE ps_item_tag17; /* Matched item tag */ /*;AN000;*/
WORD ps_strings17; /* Address of strings */ /*;AN000;*/
}; /*;AN000;*/

View File

@ -0,0 +1,233 @@
page 60,132 ;AN000;
name _msgret ;AN000;
title C to Message Retriever ;AN000;
;------------------------------------------------------------------- ;AN000;
; ;AN000;
; MODULE: _msgret ;AN000;
; ;AN000;
; PURPOSE: Supplies an interface between C programs and ;AN000;
; the DOS message retriever ;AN000;
; ;AN000;
; CALLING FORMAT: ;AN000;
; sysloadmsg(&inregs,&outregs); ;AN000;
; sysgetmsg(&inregs,&outregs); ;AN000;
; sysdispmsg(&inregs,&outregs); ;AN000;
; ;AN000;
; ;AN000;
; DATE: 5-21-87 ;AN000;
; Modified: 6/18/87 ;AN000;
; ;AN000;
;------------------------------------------------------------------- ;AN000;
; ;AN000;
INCLUDE SYSMSG.INC ;PERMIT SYSTEM MESSAGE HANDLER DEFINITION ;AN000;
; ;AN000;
MSG_UTILNAME <ATTRIB> ;IDENTIFY THE COMPONENT ;AN000;
; ;AN000;
.8087 ;AN000;
_TEXT SEGMENT BYTE PUBLIC 'CODE' ;AN000;
_TEXT ENDS ;AN000;
_DATA SEGMENT WORD PUBLIC 'DATA' ;AN000;
_DATA ENDS ;AN000;
CONST SEGMENT WORD PUBLIC 'CONST' ;AN000;
CONST ENDS ;AN000;
_BSS SEGMENT WORD PUBLIC 'BSS' ;AN000;
_BSS ENDS ;AN000;
DGROUP GROUP CONST, _BSS, _DATA ;AN000;
ASSUME CS: _TEXT, DS: _TEXT, SS: DGROUP, ES: DGROUP ;AN000;
; ;AN000;
public _sysloadmsg ;AN000;
public _sysgetmsg ;AN000;
public _sysdispmsg ;AN000;
; ;AN000;
;------------------------------------------------------------------- ;AN000;
;------------------------------------------------------------------- ;AN000;
; ;AN000;
_DATA segment ;AN000;
.XLIST ;AN000;
.XCREF ;AN000;
; MSG_SERVICES <MSGDATA> ;DATA AREA FOR THE MESSAGE HANDLER ;AN000;
MSG_SERVICES <MSGDATA> ;DATA AREA FOR THE MESSAGE HANDLER ;AN000;
.LIST ;AN000;
.CREF ;AN000;
_DATA ends ;AN000;
; ;AN000;
; ;AN000;
_TEXT segment ;AN000;
; ;AN000;
;------------------------------------------------------------------- ;AN000;
; ;AN000;
;DEFAULT=CHECK DOS VERSION ;AN000;
;DEFAULT=NEARmsg ;AN000;
;DEFAULT=INPUTmsg ;AN000;
;DEFAULT=NUMmsg ;AN000;
;DEFAULT=NO TIMEmsg ;AN000;
;DEFAULT=NO DATEmsg ;AN000;
; MSG_SERVICES <LOADmsg,GETmsg,DISPLAYmsg,CHARmsg,NUMmsg,INPUTmsg,FARmsg,TIMEmsg,DATEmsg> ;AN000;
; MSG_SERVICES <ATTRIB.CLA,ATTRIB.CLB,ATTRIB.CL1,ATTRIB.CL2> ;MSG TEXT ;AN000;
.XLIST ;AN000;
.XCREF ;AN000;
MSG_SERVICES <LOADmsg,GETmsg,DISPLAYmsg,CHARmsg,NUMmsg,INPUTmsg,FARmsg,TIMEmsg,DATEmsg> ;AN000;
MSG_SERVICES <ATTRIB.CLA,ATTRIB.CLB,ATTRIB.CL1,ATTRIB.CL2> ;MSG TEXT ;AN000;
.LIST ;AN000;
.CREF ;AN000;
; ;AN000;
;------------------------------------------------------------------- ;AN000;
_sysloadmsg proc near ;AN000;
push bp ; save user's base pointer ;AN000;
mov bp,sp ; set bp to current sp ;AN000;
push di ; save some registers ;AN000;
push si ;AN000;
; ;AN000;
; copy C inregs into proper registers ;AN000;
; ;AN000;
mov di,[bp+4] ; fix di (arg 0) ;AN000;
; ;AN000;
mov ax,[di+0ah] ; load di ;AN000;
push ax ; the di value from inregs is now on stack ;AN000;
; ;AN000;
mov ax,[di+00] ; get inregs.x.ax ;AN000;
mov bx,[di+02] ; get inregs.x.bx ;AN000;
mov cx,[di+04] ; get inregs.x.cx ;AN000;
mov dx,[di+06] ; get inregs.x.dx ;AN000;
mov si,[di+08] ; get inregs.x.si ;AN000;
pop di ; get inregs.x.di from stack ;AN000;
; ;AN000;
push bp ; save base pointer ;AN000;
; ;AN000;
;------------------------------------------------------------------- ;AN000;
call sysloadmsg ; call the message retriever ;AN000;
;------------------------------------------------------------------- ;AN000;
; ;AN000;
pop bp ; restore base pointer ;AN000;
push di ; the di value from call is now on stack ;AN000;
mov di,[bp+6] ; fix di (arg 1) ;AN000;
; ;AN000;
mov [di+00],ax ; load outregs.x.ax ;AN000;
mov [di+02],bx ; load outregs.x.bx ;AN000;
mov [di+04],cx ; load outregs.x.cx ;AN000;
mov [di+06],dx ; load outregs.x.dx ;AN000;
mov [di+08],si ; load outregs.x.si ;AN000;
; ;AN000;
lahf ; get flags into ax ;AN000;
mov al,ah ; move into low byte ;AN000;
mov [di+0ch],ax ; load outregs.x.cflag ;AN000;
; ;AN000;
pop ax ; get di from stack ;AN000;
mov [di+0ah],ax ; load outregs.x.di ;AN000;
; ;AN000;
pop si ; restore registers ;AN000;
pop di ;AN000;
mov sp,bp ; restore sp ;AN000;
pop bp ; restore user's bp ;AN000;
ret ;AN000;
_sysloadmsg endp ;AN000;
; ;AN000;
; ;AN000;
_sysgetmsg proc near ;AN000;
push bp ; save user's base pointer ;AN000;
mov bp,sp ; set bp to current sp ;AN000;
push di ; save some registers ;AN000;
push si ;AN000;
; ;AN000;
; copy C inregs into proper registers ;AN000;
; ;AN000;
mov di,[bp+4] ; fix di (arg 0) ;AN000;
; ;AN000;
mov ax,[di+0ah] ; load di ;AN000;
push ax ; the di value from inregs is now on stack ;AN000;
; ;AN000;
mov ax,[di+00] ; get inregs.x.ax ;AN000;
mov bx,[di+02] ; get inregs.x.bx ;AN000;
mov cx,[di+04] ; get inregs.x.cx ;AN000;
mov dx,[di+06] ; get inregs.x.dx ;AN000;
mov si,[di+08] ; get inregs.x.si ;AN000;
pop di ; get inregs.x.di from stack ;AN000;
; ;AN000;
push bp ; save base pointer ;AN000;
; ;AN000;
;------------------------------------------------------------------- ;AN000;
call sysgetmsg ; call the message retriever ;AN000;
;------------------------------------------------------------------- ;AN000;
; ;AN000;
pop bp ; restore base pointer ;AN000;
push di ; the di value from call is now on stack ;AN000;
mov di,[bp+6] ; fix di (arg 1) ;AN000;
; ;AN000;
mov [di+00],ax ; load outregs.x.ax ;AN000;
mov [di+02],bx ; load outregs.x.bx ;AN000;
mov [di+04],cx ; load outregs.x.cx ;AN000;
mov [di+06],dx ; load outregs.x.dx ;AN000;
mov [di+08],si ; load outregs.x.si ;AN000;
; ;AN000;
lahf ; get flags into ax ;AN000;
mov al,ah ; move into low byte ;AN000;
mov [di+0ch],ax ; load outregs.x.cflag ;AN000;
; ;AN000;
pop ax ; get di from stack ;AN000;
mov [di+0ah],ax ; load outregs.x.di ;AN000;
; ;AN000;
pop si ; restore registers ;AN000;
pop di ;AN000;
mov sp,bp ; restore sp ;AN000;
pop bp ; restore user's bp ;AN000;
ret ;AN000;
_sysgetmsg endp ;AN000;
; ;AN000;
; ;AN000;
_sysdispmsg proc near ;AN000;
push bp ; save user's base pointer ;AN000;
mov bp,sp ; set bp to current sp ;AN000;
push di ; save some registers ;AN000;
push si ;AN000;
; ;AN000;
; copy C inregs into proper registers ;AN000;
; ;AN000;
mov di,[bp+4] ; fix di (arg 0) ;AN000;
; ;AN000;
mov ax,[di+0ah] ; load di ;AN000;
push ax ; the di value from inregs is now on stack ;AN000;
; ;AN000;
mov ax,[di+00] ; get inregs.x.ax ;AN000;
mov bx,[di+02] ; get inregs.x.bx ;AN000;
mov cx,[di+04] ; get inregs.x.cx ;AN000;
mov dx,[di+06] ; get inregs.x.dx ;AN000;
mov si,[di+08] ; get inregs.x.si ;AN000;
pop di ; get inregs.x.di from stack ;AN000;
; ;AN000;
push bp ; save base pointer ;AN000;
; ;AN000;
;------------------------------------------------------------------- ;AN000;
call sysdispmsg ; call the message retriever ;AN000;
;------------------------------------------------------------------- ;AN000;
; ;AN000;
pop bp ; restore base pointer ;AN000;
push di ; the di value from call is now on stack ;AN000;
mov di,[bp+6] ; fix di (arg 1) ;AN000;
; ;AN000;
mov [di+00],ax ; load outregs.x.ax ;AN000;
mov [di+02],bx ; load outregs.x.bx ;AN000;
mov [di+04],cx ; load outregs.x.cx ;AN000;
mov [di+06],dx ; load outregs.x.dx ;AN000;
mov [di+08],si ; load outregs.x.si ;AN000;
; ;AN000;
lahf ; get flags into ax ;AN000;
mov al,ah ; move into low byte ;AN000;
mov [di+0ch],ax ; load outregs.x.cflag ;AN000;
; ;AN000;
pop ax ; get di from stack ;AN000;
mov [di+0ah],ax ; load outregs.x.di ;AN000;
; ;AN000;
pop si ; restore registers ;AN000;
pop di ;AN000;
mov sp,bp ; restore sp ;AN000;
pop bp ; restore user's bp ;AN000;
ret ;AN000;
_sysdispmsg endp ;AN000;
; ;AN000;
; ;AN000;
_TEXT ends ; end code segment ;AN000;
include msgdcl.inc
end ;AN000;


View File

@ -0,0 +1,107 @@
page 60,132 ;AN000;
name _parse ;AN000;
title C to PARSER interface ;AN000;
;------------------------------------------------------------------- ;AN000;
; ;AN000;
; MODULE: _parse ;AN000;
; ;AN000;
; PURPOSE: Supplies an interface between C programs and ;AN000;
; the DOS parser ;AN000;
; ;AN000;
; CALLING FORMAT: ;AN000;
; parse(&inregs,&outregs); ;AN000;
; ;AN000;
; DATE: 5-21-87 ;AN000;
; ;AN000;
;------------------------------------------------------------------- ;AN000;
; ;AN000;
; extrn sysparse:far ;AN000;
; ;AN000;
public _parse ;AN000;
; ;AN000;
;------------------------------------------------------------------- ;AN000;
FarSW equ 0 ; make sysparse be a NEAR proc ;AN000;
TimeSW equ 0 ; Check time format ;AN000;
FileSW equ 1 ; Check file specification ;AN000;
CAPSW equ 1 ; Perform CAPS if specified ;AN000;
CmpxSW equ 0 ; Check complex list ;AN000;
NumSW equ 1 ; Check numeric value ;AN000;
KeySW equ 1 ; Support keywords ;AN000;
SwSW equ 1 ; Support switches ;AN000;
Val1SW equ 1 ; Support value definition 1 ;AN000;
Val2SW equ 1 ; Support value definition 2 ;AN000;
Val3SW equ 1 ; Support value definition 3 ;AN000;
DrvSW equ 0 ; Support drive only format ;AN000;
QusSW equ 1 ; Support quoted string format ;AN000;
;------------------------------------------------------------------- ;AN000;
DGROUP GROUP _DATA
PGROUP GROUP _TEXT
_DATA segment byte public 'DATA' ;AN000;
BASESW = 1 ;SPECIFY, PSDATA POINTED TO BY "DS"
INCSW = 0 ;PSDATA.INC IS ALREADY INCLUDED
INCLUDE PSDATA.INC ;PARSER'S WORK SPACE
_DATA ends ;AN000;
_TEXT segment byte public 'CODE' ;AN000;
ASSUME CS: PGROUP ;AN000;
ASSUME DS: DGROUP ;AN000;
;------------------------------------------------------------------- ;AN000;
.xlist ;AN000;
include parse.asm ; include the parser ;AN000;
.list ;AN000;
;------------------------------------------------------------------- ;AN000;
; ;AN000;
_parse proc near ;AN000;
push bp ; save user's base pointer ;AN000;
mov bp,sp ; set bp to current sp ;AN000;
push di ; save some registers ;AN000;
push si ;AN000;
; ;AN000;
; copy C inregs into proper registers ;AN000;
; ;AN000;
mov di,[bp+4] ; fix di (arg 0) ;AN000;
; ;AN000;
mov ax,[di+0ah] ; load di ;AN000;
push ax ; the di value from inregs is now on stack ;AN000;
; ;AN000;
mov ax,[di+00] ; get inregs.x.ax ;AN000;
mov bx,[di+02] ; get inregs.x.bx ;AN000;
mov cx,[di+04] ; get inregs.x.cx ;AN000;
mov dx,[di+06] ; get inregs.x.dx ;AN000;
mov si,[di+08] ; get inregs.x.si ;AN000;
pop di ; get inregs.x.di from stack ;AN000;
; ;AN000;
push bp ; save base pointer ;AN000;
; ;AN000;
;------------------------------------------------------------------- ;AN000;
call sysparse ; call the parser ;AN000;
;------------------------------------------------------------------- ;AN000;
; ;AN000;
pop bp ; restore base pointer ;AN000;
push di ; the di value from call is now on stack ;AN000;
mov di,[bp+6] ; fix di (arg 1) ;AN000;
; ;AN000;
mov [di+00],ax ; load outregs.x.ax ;AN000;
mov [di+02],bx ; load outregs.x.bx ;AN000;
mov [di+04],cx ; load outregs.x.cx ;AN000;
mov [di+06],dx ; load outregs.x.dx ;AN000;
mov [di+08],si ; load outregs.x.si ;AN000;
; ;AN000;
lahf ; get flags into ax ;AN000;
mov al,ah ; move into low byte ;AN000;
mov [di+0ch],ax ; load outregs.x.cflag ;AN000;
; ;AN000;
pop ax ; get di from stack ;AN000;
mov [di+0ah],ax ; load outregs.x.di ;AN000;
; ;AN000;
pop si ; restore registers ;AN000;
pop di ;AN000;
mov sp,bp ; restore sp ;AN000;
pop bp ; restore user's bp ;AN000;
ret ;AN000;
_parse endp ;AN000;
_TEXT ends ; end code segment ;AN000;
end ;AN000;


View File

@ -0,0 +1,223 @@
/* 0 */
/*-----------------------------------------------------------------------*/
/*- -*/
/*- FILE: BACKPARS.H -*/
/*- -*/
/*- PURPOSE: Defines structures and DEFINES for the DOS PARSE -*/
/*- service routines. -*/
/*- -*/
/*- DATE: 6/5/87 -*/
/*- -*/
/*-----------------------------------------------------------------------*/
/**********************************************************/
/* STRUCTURE TO DEFINE ADDITIONAL COMMAND LINE DELIMITERS */
/**********************************************************/
struct p_parms /*;AN000;4*/
{ /*;AN000;4*/
WORD parmsx_ptr; /* POINTER TO PARMS STRUCTURE *//*;AN000;4*/
BYTE p_num_extra; /* 1 SAYS THAT A DELIMITER LIST FOLLOWS */ /*;AN000;4*/
BYTE p_len_extra_delim; /* NUMBER OF ADDITIONAL DELIMITERS *//*;AN000;4*/
BYTE p_extra_delim[2]; /* ADDITIONAL DELIMITERS */ /*;AN000;4*/
}; /*;AN000;4*/
/**************************************************/
/* STRUCTURE TO DEFINE BACKUP SYNTAX REQUIREMENTS */
/**************************************************/
struct p_parmsx /*;AN000;4*/
{ /*;AN000;4*/
BYTE p_minpos; /* THERE ARE 2 REQUIRED POSITIONAL PARMS*/ /*;AN000;4*/
BYTE p_maxpos; /* THERE ARE 2 REQUIRED POSITIONAL PARMS*/ /*;AN000;4*/
WORD pos1_ptr; /* POINTER TO SOURCE FILESPEC DEF AREA*/ /*;AN000;4*/
WORD pos2_ptr; /* POINTER TO TARGET DRIVE DEF AREA*/ /*;AN000;4*/
BYTE num_sw; /* THERE ARE 7 SWITCHES (/S, /F, /M, /A, /L:, /T:, /D:) */ /*;AN000;4*/
WORD sw1_ptr; /* POINTER TO FIRST SWITCH DEFINITION AREA*//*;AN000;4*/
WORD sw2_ptr; /* POINTER TO SECOND SWITCH DEFINITION AREA*//*;AN000;4*/
WORD sw3_ptr; /* POINTER TO THIRD SWITCH DEFINITION AREA*//*;AN000;4*/
WORD sw4_ptr; /* POINTER TO FOURTH SWITCH DEFINITION AREA*//*;AN000;4*/
WORD sw5_ptr; /* POINTER TO FIFTH SWITCH DEFINITION AREA*//*;AN000;4*/
WORD num_keywords; /* NUMBER OF KEYWORDS IN BACKUP SYNTAX*/ /*;AN000;4*/
}; /*;AN000;4*/
/****************************************/
/* STRUCTURE TO DEFINE POSITIONAL PARMS */
/****************************************/
struct p_pos_blk /*;AN000;4*/
{ /*;AN000;4*/
WORD match_flag; /* Controls type matched */ /*;AN000;4*/
WORD function_flag; /* Function should be taken */ /*;AN000;4*/
WORD result_buf; /* Result buffer address */ /*;AN000;4*/
WORD value_list; /* Value list address */ /*;AN000;4*/
BYTE nid; /* # of keyword/SW synonyms (0) *//*;AN000;4*/
}; /*;AN000;4*/
/********************************/
/* STRUCTURE TO DEFINE SWITCHES */
/********************************/
struct p_sw_blk /*;AN000;4*/
{ /*;AN000;4*/
WORD p_match_flag; /* Controls type matched */ /*;AN000;4*/
WORD p_function_flag; /* Function should be taken */ /*;AN000;4*/
WORD p_result_buf; /* Result buffer address */ /*;AN000;4*/
WORD p_value_list; /* Value list address */ /*;AN000;4*/
BYTE p_nid; /* # of switches */ /*;AN000;4*/
BYTE switch1[3]; /* Save area for switch */ /*;AN000;4*/
BYTE switch2[3]; /* Save area for switch */ /*;AN000;4*/
BYTE switch3[3]; /* Save area for switch */ /*;AN000;4*/
BYTE switch4[3]; /* Save area for switch */ /*;AN000;4*/
}; /*;AN000;4*/
/* */
/*---------------------------------------------------------------------------*/
/*---------------------------------------------------------------------------*/
/**************************/
/* RETURN BUFFER FOR TIME */
/**************************/
struct timebuff /*;AN000;4*/
{ /*;AN000;4*/
BYTE t_type; /* TYPE RETURNED*/ /*;AN000;4*/
BYTE t_item_tag; /* SPACE FOR ITEM TAG*/ /*;AN000;4*/
WORD t_synonym_ptr; /* pointer to Synonym list returned */ /*;AN000;4*/
BYTE hours; /*;AN000;4*/
BYTE minutes; /*;AN000;4*/
BYTE seconds; /*;AN000;4*/
BYTE hundreds; /*;AN000;4*/
}; /*;AN000;4*/
/**************************/
/* RETURN BUFFER FOR DATE */
/**************************/
struct datebuff
{ /*;AN000;4*/
BYTE d_type; /* TYPE RETURNED*/ /*;AN000;4*/
BYTE d_item_tag; /* SPACE FOR ITEM TAG*/ /*;AN000;4*/
WORD d_synonym_ptr; /* pointer to Synonym list returned */ /*;AN000;4*/
WORD year; /*;AN000;4*/
BYTE month; /*;AN000;4*/
BYTE day; /*;AN000;4*/
}; /*;AN000;4*/
/*******************************************/
/* RETURN BUFFER FOR POSITIONAL PARAMETERS */
/*******************************************/
struct p_result_blk /*;AN000;4*/
{ /*;AN000;4*/
BYTE p_type; /* Type returned */ /*;AN000;4*/
BYTE p_item_tag; /* Matched item tag */ /*;AN000;4*/
WORD p_synonym_ptr; /* pointer to Synonym list returned *//*;AN000;4*/
DWORD p_string_ptr; /* Pointer to string /*;AN000;4*/
}; /*;AN000;4*/
/****************************************/
/* RETURN BUFFER FOR SWITCH INFORMATION */
/****************************************/
struct switchbuff /*;AN000;4*/
{ /*;AN000;4*/
BYTE sw_type; /* TYPE RETURNED*/ /*;AN000;4*/
BYTE sw_item_tag; /* Matched item tag */ /*;AN000;4*/
WORD sw_synonym_ptr; /* pointer to synonym */ /*;AN000;4*/
DWORD sw_string_ptr; /* Pointer to string */ /*;AN000;4*/
}; /*;AN000;4*/
/********************************/
/* VALUE LIST FOR /F: PARAMETER */
/********************************/
struct val_list_struct /*;AN000;pxxxx*/
{ /*;AN000;pxxxx*/
BYTE nval; /*;AN000;pxxxx*/
BYTE num_ranges; /*;AN000;pxxxx*/
BYTE num_choices; /*;AN000;pxxxx*/
BYTE num_strings; /*;AN000;pxxxx*/
BYTE item_tag01; /*;AN000;pxxxx*/
WORD val01; /*;AN000;pxxxx*/
BYTE item_tag02; /*;AN000;pxxxx*/
WORD val02; /*;AN000;pxxxx*/
BYTE item_tag03; /*;AN000;pxxxx*/
WORD val03; /*;AN000;pxxxx*/
BYTE item_tag04; /*;AN000;pxxxx*/
WORD val04; /*;AN000;pxxxx*/
BYTE item_tag05; /*;AN000;pxxxx*/
WORD val05; /*;AN000;pxxxx*/
BYTE item_tag06; /*;AN000;pxxxx*/
WORD val06; /*;AN000;pxxxx*/
BYTE item_tag07; /*;AN000;pxxxx*/
WORD val07; /*;AN000;pxxxx*/
BYTE item_tag08; /*;AN000;pxxxx*/
WORD val08; /*;AN000;pxxxx*/
BYTE item_tag09; /*;AN000;pxxxx*/
WORD val09; /*;AN000;pxxxx*/
BYTE item_tag10; /*;AN000;pxxxx*/
WORD val10; /*;AN000;pxxxx*/
BYTE item_tag11; /*;AN000;pxxxx*/
WORD val11; /*;AN000;pxxxx*/
BYTE item_tag12; /*;AN000;pxxxx*/
WORD val12; /*;AN000;pxxxx*/
BYTE item_tag13; /*;AN000;pxxxx*/
WORD val13; /*;AN000;pxxxx*/
BYTE item_tag14; /*;AN000;pxxxx*/
WORD val14; /*;AN000;pxxxx*/
BYTE item_tag15; /*;AN000;pxxxx*/
WORD val15; /*;AN000;pxxxx*/
BYTE item_tag16; /*;AN000;pxxxx*/
WORD val16; /*;AN000;pxxxx*/
BYTE item_tag17; /*;AN000;pxxxx*/
WORD val17; /*;AN000;pxxxx*/
BYTE item_tag18; /*;AN000;pxxxx*/
WORD val18; /*;AN000;pxxxx*/
BYTE item_tag19; /*;AN000;pxxxx*/
WORD val19; /*;AN000;pxxxx*/
BYTE item_tag20; /*;AN000;pxxxx*/
WORD val20; /*;AN000;pxxxx*/
BYTE item_tag21; /*;AN000;pxxxx*/
WORD val21; /*;AN000;pxxxx*/
BYTE item_tag22; /*;AN000;pxxxx*/
WORD val22; /*;AN000;pxxxx*/
BYTE item_tag23; /*;AN000;pxxxx*/
WORD val23; /*;AN000;pxxxx*/
BYTE item_tag24; /*;AN000;pxxxx*/
WORD val24; /*;AN000;pxxxx*/
BYTE item_tag25; /*;AN000;pxxxx*/
WORD val25; /*;AN000;pxxxx*/
BYTE item_tag26; /*;AN000;pxxxx*/
WORD val26; /*;AN000;pxxxx*/
BYTE item_tag27; /*;AN000;pxxxx*/
WORD val27; /*;AN000;pxxxx*/
}; /*;AN000;pxxxx*/
/*********************************/
/* VALUE TABLE FOR /F: PARAMETER */
/*********************************/
struct val_table_struct /*;AN000;pxxxx*/
{ /*;AN000;pxxxx*/
BYTE val01[7]; /*;AN000;pxxxx*/
BYTE val02[7]; /*;AN000;pxxxx*/
BYTE val03[7]; /*;AN000;pxxxx*/
BYTE val04[7]; /*;AN000;pxxxx*/
BYTE val05[7]; /*;AN000;pxxxx*/
BYTE val06[7]; /*;AN000;pxxxx*/
BYTE val07[7]; /*;AN000;pxxxx*/
BYTE val08[7]; /*;AN000;pxxxx*/
BYTE val09[7]; /*;AN000;pxxxx*/
BYTE val10[7]; /*;AN000;pxxxx*/
BYTE val11[7]; /*;AN000;pxxxx*/
BYTE val12[7]; /*;AN000;pxxxx*/
BYTE val13[7]; /*;AN000;pxxxx*/
BYTE val14[7]; /*;AN000;pxxxx*/
BYTE val15[7]; /*;AN000;pxxxx*/
BYTE val16[7]; /*;AN000;pxxxx*/
BYTE val17[7]; /*;AN000;pxxxx*/
BYTE val18[7]; /*;AN000;pxxxx*/
BYTE val19[7]; /*;AN000;pxxxx*/
BYTE val20[7]; /*;AN000;pxxxx*/
BYTE val21[7]; /*;AN000;pxxxx*/
BYTE val22[7]; /*;AN000;pxxxx*/
BYTE val23[7]; /*;AN000;pxxxx*/
BYTE val24[7]; /*;AN000;pxxxx*/
BYTE val25[7]; /*;AN000;pxxxx*/
BYTE val26[7]; /*;AN000;pxxxx*/
BYTE val27[7]; /*;AN000;pxxxx*/
}; /*;AN000;pxxxx*/

4385
v4.0/src/CMD/BACKUP/BACKUP.C Normal file

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,502 @@
/*0 */
/*-----------------------------------------------------------
/*-
/*- FILE: BACKUP.H
/*-
/*- PURPOSE: For the BACKUP utility, this file has the required
/*- BACKUP defines, message numbers, structures,
/*- and subroutine declarations.
/*-
/*---------------------------------------------------------*/
/*----------------------
/*- Utility #DEFINES...
/*----------------------*/
#define DHLENGTH 139 /* Length, in bytes, of a Disk Header */
#define DBLENGTH 70 /* Length, in bytes, of a Directory Block */
#define FHLENGTH 34 /* Length, in bytes, of a File Header */
#define BYTE unsigned char
#define WORD unsigned short
#define DWORD unsigned long
#define NOERROR 0
#define NUL 0
#define FALSE 0
#define TRUE !FALSE
#define BACKSLASH 0x5c
#define READONLYOFF 254 /* bit mask, will be ANDed with current attribute to turn off readonly bit */
#define READONLY 0x01 /* File Attributes */
#define HIDDEN 0x02
#define SYSTEM 0x04
#define VOLLABEL 0x08
#define SUBDIR 0x10
#define ARCHIVE 0x20
#define DENYALL 0x10 /* Sharing Mode */
#define DENYWRITE 0x20
#define DENYREAD 0x30
#define DENYNONE 0x40
#define READACCESS 0x00 /* Access Modes */
#define WRITEACCESS 0x01
#define READWRITE 0x02
#define NO_CP_CHECK 0x100 /*;AN000;5*/
#define SYNCHRONOUS 0x4000 /* OS/2 File Write-Through */
#define NOTSYNCHRONOUS 0x0000 /* OS/2 File Write-Through */
#define OPENDASD 0x8000 /* OS/2 Open a DASD device */
#define OPEN_IT 0x01 /*;AN000;5*/
#define CREATE_IT 0x12 /*;AN000;5*/
#define NO_INHERIT 0x80 /* Inheritance bit */
#define STDIN 0x00 /* Predefined handles */
#define STDOUT 0x01
#define STDERR 0x02
#define BOFILE 0 /* LSEEK move methods */
#define CURRPOS 1
#define EOFILE 2
#define GET 0 /* CHMOD functions */
#define SET 1
#define SSTRING 0x2000 /*;AN000;4 Parser Match Flags */
#define DATESTRING 0x1000 /*;AN000;4*/
#define TIMESTRING 0x0800 /*;AN000;4*/
#define FILESPEC 0x0200 /*;AN000;4*/
#define DRIVELETTER 0x0100 /*;AN000;4*/
#define OPTIONAL 0x0001 /*;AN000;4*/
#define CAP_FILETABLE 0x0001 /*;AN000;4 Parser Function flag*/
#define CAP_CHARTABLE 0x0002 /*;AN000;4 Parser Function flag*/
#define LABELLEN 11
#define SETLOGICALDRIVE 0x440F /*;AN000;8 */
/*--------APPEND FUNCTIONS-----------*/
#define INSTALL_CHECK 0xB700 /*;AN000;2*/
#define NOT_INSTALLED 0 /*;AN000;2*/
#define GET_APPEND_VER 0xB702 /*;AN000;2*/
#define NET_APPEND 1 /*;AN000;2*/
#define DOS_APPEND 2 /*;AN000;2*/
#define GET_STATE 0xB706 /*;AN000;2*/
#define SET_STATE 0xB707 /*;AN000;2*/
#define APPEND_X_BIT 0x8000 /*;AN000;2*/
#define ACTIONHOOK 2
#define CTRLC 1
#define CTRLBREAK 4
#define EOL -1 /*;AN000;4*/
#define QUOTED_STRING 9 /*;AN000;4*/
#define RET_DATE 7 /*;AN000;4*/
#define RET_TIME 8 /*;AN000;4*/
#define CPSW_ACTIVE 1 /*;AN000;3*/
#define CPSW_NOTACTIVE 0 /*;AN000;3*/
#define GET_CPSW 0x3303 /*;AN000;3*/
#define CARRY 0x0001 /*;AN000;*/
/***********************************/
/* Utility-specific definitions */
/***********************************/
#define ROOTDIR 0
#define BACKUPDIR 1
#define PUT_SEG(fp,seg) (*((unsigned *)&(fp)+1)) = (unsigned) seg
#define PUT_OFF(fp,off) (*((unsigned *)&(fp))) = (unsigned) off
#define MAXMSGLEN 160
#define PATHLEN 64
#define MAX_RETRY_OPEN_COUNT 5
#define RETCODE_NO_ERROR 0 /* Errorlevels */
#define RETCODE_NO_FILES 1
#define RETCODE_SHARE_ERROR 2
#define RETCODE_CTL_BREAK 3
#define RETCODE_ERROR 4
/************************************************/
/* NOTE FROM PARSER SUBROUTINE !!!!! */
/************************************************/
/* The SECONDS bits in the DOS Directory are in */
/* 2-second increments. Therefore, div by 2, */
/* take the integer portion and use in search. */
/* Note that files can be backed up that were */
/* modified 1 second before the time that a user*/
/* enters, which is better than not backing up */
/* a file that was modified at exactly that time*/
/************************************************/
/*-------------------------------------------*/
/*------ BACKUP messages --------*/
/*-------------------------------------------*/
#define BAD_DOS_VER 1 /*;AN000;6*/
#define INSUFF_MEMORY 2 /*;AN000;6*/
#define INV_DRIVE 6 /*;AN000;6*/
#define INV_DATE 7 /*;AN000;6*/
#define INV_TIME 8 /*;AN000;6*/
#define INV_PATH 11 /*;AN000;6*/
#define NO_SOURCE 12 /*;AN000;6*/
#define NO_TARGET 13 /*;AN000;6*/
#define SRC_AND_TGT_SAME 14 /*;AN000;6*/
#define ERR_EXEC_FORMAT 15 /*;AN000;6*/
#define CANT_FIND_FORMAT 16 /*;AN000;d178*/
#define CANT_OPEN_LOGFILE 17 /*;AN000;6*/
#define LOGGING 18 /*;AN000;6*/
#define NOTLASTMSG 19 /*;AN000;6*/
#define ERASEMSG 20 /*;AN000;6*/
#define FERASEMSG 21 /*;AN000;6*/
#define BUDISKMSG 22 /*;AN000;6*/
#define SEQUENCEMSG 23 /*;AN000;6*/
#define NONEFNDMSG 24 /*;AN000;6*/
#define INSERTSOURCE 25 /*;AN000;6*/
#define INSERTTARGET 26 /*;AN000;6*/
#define CONFLICTMSG 27 /*;AN000;6*/
#define LASTDISKMSG 28 /*;AN000;6*/
#define INVTARGET 29 /*;AN000;6*/
#define LASTNOTBACKUP 30 /*;AN000;6*/
#define FDISKFULLMSG 31 /*;AN000;6*/
#define LOGFILE_TARGET_FULL 32 /*;AN000;6*/
#define PRESS_ANY_KEY 33 /*;AN000;6*/
#define CRLF 34 /*;AN000;6*/
#define CANT_FORMAT_HARDFILE 35 /*;AN000;/*
/*------------------------------------*/
/*- MESSAGE CLASSES -*/
/*------------------------------------*/
#define EXTENDED 1 /*;AN000;6*/
#define PARSEERROR 2 /*;AN000;6*/
#define UTIL_MSG -1 /*;AN000;6*/
#define NOWAIT 0 /*;AN000;6*/
#define WAIT 0xc8 /*;AN000;6*/
/*-------------------------------------------------------------*/
/*- CONTROL BLOCK FOR EACH BACKUP DISKETTE */
/*-------------------------------------------------------------*/
/*- THIS STRUCTURE WILL MAKE UP THE FIRST DH_DHLength BYTES */
/*- OF THE control.xxx FILE ON THE BACKUP TARGET. */
/*- IT IDENTIFIES THE DISK AS BEING A BACKUP, AND INCLUDES */
/*- DISKETTE SEQUENCE NUMBER AND A FLAG INDICATING IF THIS */
/*- IS THE LAST TARGET. */
/*-------------------------------------------------------------*/
#define LAST_TARGET 0xFF
#define NOT_LAST_TARGET 0x00
struct Disk_Header
{
BYTE DH_Length; /* Length, in bytes, of disk header */
BYTE DH_Identifier[8]; /* Identifies disk as a backup */
BYTE DH_Sequence; /* Backup diskette seq num (1-255) */
BYTE DH_reserved [128]; /* Save area for nothing */
BYTE DH_LastDisk; /* Indicates if this is last target */
/* 0xFF if last target, 0 otherwise */
};
/*----------------------------------------------------------------------*/
/*- DIRECTORY BLOCK */
/*----------------------------------------------------------------------*/
/*- THIS STRUCTURE IS WRITTEN TO THE control.xxx FILE AT LEAST ONCE */
/*- FOR EACH SUBDIRECTORY, INCLUDING THE ROOT, BACKED UP. IT CONTAINS */
/*- THE PATH TO THAT DIRECTORY, THE NUMBER OF FILES FROM THAT */
/*- DIRECTORY THAT ARE BACKED UP ON CURRENT TARGET, AND THE OFFSET */
/*- OF THE NEXT DIRECTORY BLOCK ON THAT DISKETTE, IF ONE EXISTS. */
/*- IF THERE ARE NO OTHER DIRECTORY BLOCKS, IT EQUALS 0xffffffff. */
/*----------------------------------------------------------------------*/
#define LAST_DB 0xFFFFFFFF
struct Dir_Block
{
BYTE DB_Length; /* Length, in bytes, of dir block */
BYTE DB_Path[63];
/* ASCII path of this directory, */
/* drive letter omitted */
WORD DB_NumEntries; /* Num of filenames currently in list*/
DWORD DB_NextDB; /* Offset of next directory block */
}; /* =0xffffffff if there are no more*/
/* on current target */
/*--------------------------------------------------------------------*/
/*- CONTROL BLOCK FOR EACH BACKED-UP FILE */
/*--------------------------------------------------------------------*/
/*- THIS STRUCTURE WILL BE REPEATED AFTER THE DIRECTORYBLOCK ONCE */
/*- FOR EACH FILE BACKED UP FROM THAT DIRECTORY. IT CONTAINS THE */
/*- FILENAME, DIRECTORY INFORMATION, AND OTHER NECESSARY INFORMATION. */
/*--------------------------------------------------------------------*/
#define NOTLASTPART 0
#define LASTPART 1
#define NOTSUCCESSFUL 0
#define SUCCESSFUL 2
#define EXT_ATTR 4 /*;AN000;3*/
struct File_Header
{
BYTE FH_Length; /* Length, in bytes, of file header */
BYTE FH_FName[12]; /* ASCII file name (from directory)*/
BYTE FH_Flags; /* bit 0=1 if last part of file */
/* bit 1=1 if it is backed up successfully */
/* bit 2=1 if Extended Attributes are backed up (New for DOS4.00) ;AN000;3*/
DWORD FH_FLength; /* Total length of the file (from directory) */
WORD FH_FSequence; /* Sequence #, for files that span */
DWORD FH_BeginOffset; /* Offset in BACKUP.xxx where this segment begins */
DWORD FH_PartSize; /* Length of part of file on current target */
WORD FH_Attribute; /* File attribute (from directory) */
WORD FH_FTime; /* Time when file was last modified (from directory)*/
WORD FH_FDate; /* Date when file was last modified (from directory)*/
};
/*--------------------------------------------------------------------*/
/*- THIS IS THE STRUCTURE THAT IS USED IN THE LINKED LIST OF */
/*- DIRECTORIES THAT NEED TO BE PROCESSED (if /S option specified) */
/*--------------------------------------------------------------------*/
struct node
{
struct node *np;
char path[PATHLEN+15];
};
/*--------------------------------------------------------------------*/
/*- THIS IS THE STRUCTURE THAT IS USED BY THE DOS FUNCTION */
/*- "RETURN COUNTRY INFORMATION" */
/*--------------------------------------------------------------------*/
struct ctry_info_blk
{
WORD country_code;
WORD code_page;
WORD date_format;
#define USA 0
#define EUR 1
#define JAP 2
BYTE currency_symbol[5];
WORD thousands_separator;
WORD decimal_Separator;
WORD date_separator;
WORD time_separator;
BYTE currency_format;
BYTE num_sig_dec_dig_in_currency;
BYTE time_format;
DWORD case_map_call;
WORD data_list_separator;
WORD reserved[5];
};
/*------------------------------------------------------------------------*/
/*- THIS STRUCTURE IS USED BY THE DOS MESSAGE HANDLER SERVICE ROUTINES -*/
/*------------------------------------------------------------------------*/
/************************************************/
/* Substitution List for Message Retriever */
/************************************************/
/*-----------------------
; SUBLIST Equates
;------------------------*/
#define SUBLIST_SIZE 11 /*;AN000;6*/
#define LEFT_ALIGN 0x0 /*;AN000;600xxxxxx */
#define RIGHT_ALIGN 0x80 /*;AN000;610xxxxxx */
#define CHAR_FIELD_CHAR 0x0 /*;AN000;6a0000000 */
#define CHAR_FIELD_ASCIIZ 0x10 /*;AN000;6a0010000 */
#define UNSGN_BIN_BYTE 0x11 /*;AN000;6a0010001 - Unsigned BINary to Decimal CHARacter */
#define UNSGN_BIN_WORD 0x21 /*;AN000;6a0100001 */
#define UNSGN_BIN_DWORD 0x31 /*;AN000;6a0110001 */
/*---------------------------------------------*/
/*- Message substitution list structure -*/
/*---------------------------------------------*/
struct subst_list /*;AN000;6*/
{ /*;AN000;6*/
BYTE sl_size1; /* Size of List */ /*;AN000;6*/
BYTE zero1; /* Reserved */ /*;AN000;6*/
char far *value1; /* Time, date, or ptr to data item*/ /*;AN000;6*/
BYTE one; /* n of %n */ /*;AN000;6*/
BYTE flags1; /* Data Type flags */ /*;AN000;6*/
BYTE max_width1; /* Maximum FIELD width */ /*;AN000;6*/
BYTE min_width1; /* Minimum FIELD width */ /*;AN000;6*/
BYTE pad_char1; /* Character for pad FIELD */ /*;AN000;6*/
BYTE sl_size2; /* Size of List */ /*;AN000;6*/
BYTE zero2; /* Reserved */ /*;AN000;6*/
char far *value2; /* Time; date; or ptr to data item*/ /*;AN000;6*/
BYTE two; /* n of %n */ /*;AN000;6*/
BYTE flags2; /* Data Type flags */ /*;AN000;6*/
BYTE max_width2; /* Maximum FIELD width */ /*;AN000;6*/
BYTE min_width2; /* Minimum FIELD width */ /*;AN000;6*/
BYTE pad_char2; /* Character for pad FIELD */ /*;AN000;6*/
}; /*;AN000;6*/
/*----------------------------------*/
/*- EXTENDED OPEN PARAMETER LIST -*/
/*----------------------------------*/
#define EXTATTBUFLEN 4086 /*;AN000;3*/
struct parm_list /*;AN000;3*/
{ /*;AN000;3*/
DWORD ext_attr_addr; /*;AN000;3*/
WORD num_additional; /*;AN000;3*/
BYTE id_io_mode; /*;AN000;3*/
WORD io_mode; /*;AN000;3*/
}; /*;AN000;3*/
/* */
/*----------------------------------------------------*/
/*- SUBROUTINE DECLARATIONS -*/
/*----------------------------------------------------*/
int cdecl sprintf(char *, char *, ...);
int cdecl printf(char *,...);
void alloc_buffer(void);
void alloc_first_node(void);
struct node * alloc_node(unsigned int);
void check_appendX(void); /*;AN000;2*/
void alloc_seg(void);
void build_ext(int);
void change_levels(void);
void check_date(WORD,BYTE,BYTE); /*;AN000;4*/
void check_DOS_version(void);
void check_drive_validity(int,char * []);
void check_for_device_names(char * []); /*;AN000;p2592*/
void check_last_target(void);
void check_path_validity(char * []);
void check_time(BYTE,BYTE,BYTE,BYTE); /*;AN000;4*/
void clean_up_and_exit(void);
void close_file(WORD);
void close_out_current_target(void);
void control_break_handler(void);
void create_target(void);
void datetime(void);
void delete(char *);
void delete_files(char);
long disk_free_space(void);
void display_it(int,WORD,int,BYTE,BYTE); /*;AN000;6*/
void display_msg(int);
void do_backup(void);
void do_copy(void);
void do_dos_error(WORD);
extern unsigned far pascal set_int24_vector(void); /*;AN000;*/
void error_exit(int);
WORD exist(char *);
WORD extended_open(WORD,WORD,char far *,WORD); /*;AN000;5*/
void file_sharing_error(void); /*;AN000;9*/
char far * far_ptr(WORD,WORD);
void findclose(WORD);
void find_all_subdirs(void);
void find_first(char *,WORD *,struct FileFindBuf *,WORD);
void find_first_file(void);
void find_format(void); /*;AN000;d178*/
void find_next(WORD,struct FileFindBuf *);
void find_next_file(void);
void find_the_first(void);
void find_the_next(void);
void format_target(void);
void free_seg(unsigned);
WORD get_attribute(char *);
void get_current_dir(WORD,char *);
WORD get_current_drive(void);
void get_country_info(void);
void get_diskette(void);
void get_drive_types(void);
void get_extended_attributes(WORD); /*;AN000;3 */
void get_first_target(void);
void get_hardfile(void);
void get_next_target(void);
void get_path(char *); /*;AN002;*/
WORD handle_open(char *,WORD);
WORD handle_read(WORD,WORD,char far *);
WORD handle_write(WORD,WORD,char far *);
void init(void); /*;AN000;6*/
void insert_node(char *);
WORD ioctl(WORD);
void label_target_drive(void);
DWORD lseek(WORD,BYTE,DWORD);
int main(int, char * []);
void mark_as_last_target(void);
void mark_as_not_last_target(void);
void mark_files_read_only(void);
void open_logfile(void);
void open_source_file(void);
void open_target(void);
void parser(int,char * []); /*;AN000;4*/
void parse_error(WORD,WORD); /*;AN000;4*//*;AN008;*/
void parse_init(void); /*;AN000;4*/
void process_switch(void); /*;AN000;4*//*;AN008;*/
void put_disk_header(void);
void put_new_db(void);
void put_new_fh(void);
void remove_last_backslash_from_BDS(void);
void remove_node(void);
void replace_volume_label(char *);
void reset_archive_bit(char *);
void restore_default_directories(void);
void save_current_dirs(void);
void see_if_it_should_be_backed_up(void);
void set_attribute(char *,WORD);
void set_vectors(void); /*;AN000;*/
void set_default_dir(void);
void set_default_drive(WORD);
void setsignal(WORD,WORD);
void show_path(void);
char *strcat(char *,const char *); /* */
size_t strlen(const char *); /* */
char *strcpy(char *, const char *); /* */
char *strncpy(char *, const char *, unsigned int); /* */
int strncmp(const char *,const char *,unsigned int);/* */
int strcmp(const char *,const char *); /* */
void terminate(void);
void update_db_entries(WORD);
void update_fh_entries(void);
/***** void write_extended_attributes(void); /*;AN000;3*/
WORD write_till_target_full(WORD,WORD);
void write_to_control_file(char far *,WORD);
void write_to_target(WORD);
void xlat(char *,char *); /*;AN000;*/
extern void sysloadmsg(union REGS *, union REGS *); /*;AN000;6*/
extern void update_logfile(union REGS *, union REGS *); /*;AN000;9*/
extern void sysdispmsg(union REGS *, union REGS *); /*;AN000;6*/
extern void parse (union REGS *, union REGS *); /*;AN000;4*/
/*-------------------------------*/
/*- From COMSUB.H */
/*-------------------------------*/
/* convert character to uppercase */
extern int com_toupper(
unsigned char ); /* character to be converted to uppercase */
/* search the first occurrence of a character in a string */
extern char *com_strchr(
unsigned char *, /* a source string */
unsigned char ); /* a character to be searched */
/* search the last charater occurrence in a string */
extern unsigned char
*com_strrchr(
unsigned char *, /* source string */
unsigned char ); /* target string */

View File

@ -0,0 +1,52 @@
;==========================================================
:util BACKUP ;AN000;
;---------
:class A
;---------
:use 1 COMMON1 ;AN000; ;For "Incorrect DOS version
:def 2 CR,LF,"Insufficient memory",CR,LF ;AN000;
:def 6 CR,LF,"Invalid drive specification",CR,LF ;AN000;
:use 7 COMMON23 ;AN000; ;For "Invalid date
:use 8 COMMON24 ;AN000; ;For "Invalid time
:use 11 COMMON25 ;AN000; ;For "Invalid path
:use 12 COMMON26 ;AN000; ;For "No source drive specified
:use 13 COMMON27 ;AN000; ;For "No target drive specified
:def 14 CR,LF,"Source and target drives are the same",CR,LF ;AN000;
:def 15 CR,LF,"Error executing FORMAT",CR,LF ;AN000;d178
:def 16 CR,LF,"Cannot find FORMAT.COM",CR,LF ;AN000;d178
:def 17 CR,LF,"Error opening logfile",CR,LF ;AN000;
:def 18 CR,LF,"Logging to file %1",CR,LF ;AN000;
:def 19 CR,LF,"Last backup diskette not inserted",CR,LF ;AN000;
:def 20 CR,LF,"Warning! Files in the target drive",CR,LF ;AN000;
"%1:\ root directory will be erased",CR,LF ;AN000;
:def 21 CR,LF,"Warning! Files in the target drive",CR,LF ;AN000;
"%1:\BACKUP directory will be erased",CR,LF ;AN000;
:def 22 CR,LF,"*** Backing up files to drive %1: ***",CR,LF ;AN000;
:def 23 "Diskette Number: %1",CR,LF ;AN000;
:def 24 CR,LF,"Warning! No files were found to back up",CR,LF ;AN000;
:def 25 CR,LF,"Insert backup source diskette in drive %1:",CR,LF ;AN000;
:def 26 CR,LF,"Insert backup diskette %1 in drive %2:",CR,LF ;AN000;
:def 27 CR,LF,"*** Not able to backup file ***",CR,LF ;AN000;
:def 28 CR,LF,"Insert last backup diskette in drive %1:",CR,LF ;AN000;
:def 29 CR,LF,"Target can not be used for backup",CR,LF ;AN000;
:def 30 CR,LF,"*** Last file not backed up ***",CR,LF ;AN000;
:def 31 CR,LF,"Fixed backup device %1: is full",CR,LF ;AN000;
:def 32 CR,LF,"Disk full error writing to BACKUP Log File",CR,LF ;AN000;
;AN000;
:use 33 COMMON28 ;AN000; ;For "Press any key to continue . . .
:def 34 CR,LF ;AN000;
:def 35 CR,LF,"Cannot FORMAT nonremovable drive %1:",CR,LF ;AN000;
:end ;AN000;
;==========================================================

View File

@ -0,0 +1,45 @@
#************************** makefile for cmd\backup ***************************
cflags = -AS -Od -Zp $(extcsw)
msg =..\..\messages
dos =..\..\dos
inc =..\..\inc
hinc =..\..\h
map =..\..\mapper
here =..\cmd\backup
#
####################### dependencies begin here. #########################
#
all: backup.com
$(map)\mapper.lib:
cd $(map)
nmake
cd $(here)
_parse.obj: _parse.asm \
$(inc)\parse.asm \
$(inc)\psdata.inc \
makefile
backup.ctl: backup.skl \
$(msg)\$(COUNTRY).MSG
_msgret.obj: _msgret.asm \
backup.ctl \
$(inc)\msgserv.asm \
$(inc)\sysmsg.inc \
$(inc)\versiona.inc \
$(inc)\copyrigh.inc \
makefile
backup.obj: backup.c backpars.h backup.h makefile \
$(hinc)\doscalls.h
backup.com: backup.obj _parse.obj _msgret.obj \
$(map)\mapper.lib $(inc)\comsubs.lib
link /NOE backup + _parse + _msgret,,,$(map)\mapper + $(inc)\comsubs;
convert backup.exe backup.com
del backup.exe

View File

@ -0,0 +1,268 @@
page 60,132
name _msgret
title C to Message Retriever
;-------------------------------------------------------------------
;
; MODULE: _msgret
;
; PURPOSE: Supplies an interface between C programs and
; the DOS 3.30 message retriever
;
; CALLING FORMAT:
; sysloadmsg(&inregs,&outregs);
; sysdispmsg(&inregs,&outregs);
; sysgetmsg(&inregs,&outregs);
;
; DATE: 5-21-87
;
;-------------------------------------------------------------------
INCLUDE SYSMSG.INC ;PERMIT SYSTEM MESSAGE HANDLER DEFINITION ;AN000;
MSG_UTILNAME <BACKUP> ;IDENTIFY THE COMPONENT ;AN000;
.8087
_TEXT SEGMENT BYTE PUBLIC 'CODE'
_TEXT ENDS
_DATA SEGMENT WORD PUBLIC 'DATA'
_DATA ENDS
CONST SEGMENT WORD PUBLIC 'CONST'
CONST ENDS
_BSS SEGMENT WORD PUBLIC 'BSS'
_BSS ENDS
DGROUP GROUP CONST, _BSS, _DATA
ASSUME CS: _TEXT, DS: _TEXT, SS: DGROUP, ES: DGROUP
public _sysloadmsg
public _sysdispmsg
public _update_logfile
;-------------------------------------------------------------------
;-------------------------------------------------------------------
_DATA segment
.XLIST
.XCREF
MSG_SERVICES <MSGDATA> ;DATA AREA FOR THE MESSAGE HANDLER ;AN000;
.LIST
.CREF
_DATA ends
_TEXT segment
;-------------------------------------------------------------------
;DEFAULT=CHECK DOS VERSION
;DEFAULT=NEARmsg
;DEFAULT=INPUTmsg
;DEFAULT=NUMmsg
;DEFAULT=NO TIMEmsg
;DEFAULT=NO DATEmsg
.XLIST
.XCREF
MSG_SERVICES <LOADmsg,DISPLAYmsg,GETmsg,INPUTmsg,CHARmsg,NUMmsg,TIMEmsg,DATEmsg,FARmsg> ;AN000;
MSG_SERVICES <BACKUP.CTL,BACKUP.CLA,BACKUP.CL1,BACKUP.CL2> ;AN000;
.LIST
.CREF
;-------------------------------------------------------------------
_sysloadmsg proc near
push bp ; save user's base pointer
mov bp,sp ; set bp to current sp
push di ; save some registers
push si
; copy C inregs into proper registers
mov di,[bp+4] ; fix di (arg 0)
;-------------------------------------------------------------------
mov ax,[di+0ah] ; load di
push ax ; the di value from inregs is now on stack
mov ax,[di+00] ; get inregs.x.ax
mov bx,[di+02] ; get inregs.x.bx
mov cx,[di+04] ; get inregs.x.cx
mov dx,[di+06] ; get inregs.x.dx
mov si,[di+08] ; get inregs.x.si
pop di ; get inregs.x.di from stack
push bp ; save base pointer
;-------------------------------------------------------------------
call sysloadmsg ; call the message retriever
;-------------------------------------------------------------------
pop bp ; restore base pointer
push di ; the di value from call is now on stack
mov di,[bp+6] ; fix di (arg 1)
mov [di+00],ax ; load outregs.x.ax
mov [di+02],bx ; load outregs.x.bx
mov [di+04],cx ; load outregs.x.cx
mov [di+06],dx ; load outregs.x.dx
mov [di+08],si ; load outregs.x.si
lahf ; get flags into ax
mov al,ah ; move into low byte
mov [di+0ch],ax ; load outregs.x.cflag
pop ax ; get di from stack
mov [di+0ah],ax ; load outregs.x.di
;-------------------------------------------------------------------
pop si ; restore registers
pop di
mov sp,bp ; restore sp
pop bp ; restore user's bp
ret
_sysloadmsg endp
;============================================================================
;============================================================================
;============================================================================
_update_logfile proc near
push bp ; save user's base pointer
mov bp,sp ; set bp to current sp
push di ; save some registers
push si
mov di,[bp+4] ; fix di (arg 0)
;-------------------------------------------------------------------
mov ax,[di+0ah] ; load di
push ax ; the di value from inregs is now on stack
mov ax,[di+00] ; get inregs.x.ax
mov bx,[di+02] ; get inregs.x.bx
mov cx,[di+04] ; get inregs.x.cx
mov dx,[di+06] ; get inregs.x.dx
mov si,[di+08] ; get inregs.x.si
pop di ; get inregs.x.di from stack
push bp ; save base pointer
;-------------------------------------------------------------------
mov dh,-1 ; Message class, Utility message
mov cs:handle,bx ;AN000;9 Save logfile handle
mov cs:len,cx ;AN000;9 Save write length
push ds ;AN000;9
pop cs:save_ds ;AN000;9
call sysgetmsg ; call the message retriever
;-------------------------------------------------------------------
pop bp ; restore base pointer
push di ; the di value from call is now on stack
mov di,[bp+6] ; fix di (arg 1)
mov [di+00],ax ; load outregs.x.ax
mov [di+02],bx ; load outregs.x.bx
mov [di+04],cx ; load outregs.x.cx
mov [di+06],dx ; load outregs.x.dx
mov [di+08],si ; load outregs.x.si
lahf ; get flags into ax
mov al,ah ; move into low byte
mov [di+0ch],ax ; load outregs.x.cflag
pop ax ; get di from stack
mov [di+0ah],ax ; load outregs.x.di
mov cs:offst,si ;AN000;9
pop si ; restore registers
pop di
mov sp,bp ; restore sp
pop bp ; restore user's bp
mov ah,040h ;AN000;9 Write the message to logfile
mov bx,cs:handle ;AN000;9
mov cx,cs:len ;AN000;9
mov dx,cs:offst ;AN000;9
int 021h ;AN000;9
push cs:save_ds ;AN000;9
pop ds ;AN000;9
ret
handle dw ? ;AN000;9
len dw ? ;AN000;9
offst dw ? ;AN000;9
save_ds dw ? ;AN000;9
_update_logfile endp
;============================================================================
;============================================================================
;============================================================================
_sysdispmsg proc near
push bp ; save user's base pointer
mov bp,sp ; set bp to current sp
push di ; save some registers
push si
; copy C inregs into proper registers
mov di,[bp+4] ; fix di (arg 0)
;-------------------------------------------------------------------
mov ax,[di+0ah] ; load di
push ax ; the di value from inregs is now on stack
mov ax,[di+00] ; get inregs.x.ax
mov bx,[di+02] ; get inregs.x.bx
mov cx,[di+04] ; get inregs.x.cx
mov dx,[di+06] ; get inregs.x.dx
mov si,[di+08] ; get inregs.x.si
pop di ; get inregs.x.di from stack
push bp ; save base pointer
;-------------------------------------------------------------------
call sysdispmsg ; call the message retriever
;-------------------------------------------------------------------
pop bp ; restore base pointer
push di ; the di value from call is now on stack
mov di,[bp+6] ; fix di (arg 1)
mov [di+00],ax ; load outregs.x.ax
mov [di+02],bx ; load outregs.x.bx
mov [di+04],cx ; load outregs.x.cx
mov [di+06],dx ; load outregs.x.dx
mov [di+08],si ; load outregs.x.si
lahf ; get flags into ax
mov al,ah ; move into low byte
mov [di+0ch],ax ; load outregs.x.cflag
pop ax ; get di from stack
mov [di+0ah],ax ; load outregs.x.di
;-------------------------------------------------------------------
pop si ; restore registers
pop di
mov sp,bp ; restore sp
pop bp ; restore user's bp
ret
_sysdispmsg endp
;============================================================================
;============================================================================
;============================================================================
;============================================================================
;============================================================================
;============================================================================
include msgdcl.inc
_TEXT ends ; end code segment
end


View File

@ -0,0 +1,121 @@
page 60,132
name _parse
title C to PARSER interface
;-------------------------------------------------------------------
;
; MODULE: _parse
;
; PURPOSE: Supplies an interface between C programs and
; the DOS 3.30 parser
;
; CALLING FORMAT:
; parse(&inregs,&outregs);
;
; DATE: 5-21-87
;
;-------------------------------------------------------------------
; extrn sysparse:far
public _parse
include version.inc
;-------------------------------------------------------------------
FarSW equ 0 ; make sysparse be a NEAR proc
TimeSW equ 1 ; Check time format
FileSW equ 1 ; Check file specification
CAPSW equ 1 ; Perform CAPS if specified
CmpxSW equ 0 ; Check complex list
NumSW equ 0 ; Check numeric value
KeySW equ 0 ; Support keywords
SwSW equ 1 ; Support switches
Val1SW equ 0 ; Support value definition 1
Val2SW equ 0 ; Support value definition 2
if ibmcopyright
Val3SW equ 0 ; Support value definition 3
else
Val3SW equ 1 ; Support value definition 3
endif
DrvSW equ 1 ; Support drive only format
QusSW equ 0 ; Support quoted string format
IncSW equ 0 ; Dont include PSDATA, I just did it
BaseSW equ 1 ; DS points to data
;-------------------------------------------------------------------
DGROUP GROUP _DATA
PGROUP GROUP _TEXT
_DATA segment byte public 'DATA'
include psdata.inc
_DATA ends
_TEXT segment byte public 'CODE'
ASSUME CS: PGROUP
ASSUME DS: DGROUP
;-------------------------------------------------------------------
.xlist
include parse.asm ; include the parser
.list
;-------------------------------------------------------------------
_parse proc near
push bp ; save user's base pointer
mov bp,sp ; set bp to current sp
push di ; save some registers
push si
; copy C inregs into proper registers
mov di,[bp+4] ; fix di (arg 0)
;-------------------------------------------------------------------
mov ax,[di+0ah] ; load di
push ax ; the di value from inregs is now on stack
mov ax,[di+00] ; get inregs.x.ax
mov bx,[di+02] ; get inregs.x.bx
mov cx,[di+04] ; get inregs.x.cx
mov dx,[di+06] ; get inregs.x.dx
mov si,[di+08] ; get inregs.x.si
pop di ; get inregs.x.di from stack
push bp ; save base pointer
;-------------------------------------------------------------------
call sysparse ; call the parser
;-------------------------------------------------------------------
pop bp ; restore base pointer
push di ; the di value from call is now on stack
mov di,[bp+6] ; fix di (arg 1)
mov [di+00],ax ; load outregs.x.ax
mov [di+02],bx ; load outregs.x.bx
mov [di+04],cx ; load outregs.x.cx
mov [di+06],dx ; load outregs.x.dx
mov [di+08],si ; load outregs.x.si
lahf ; get flags into ax
mov al,ah ; move into low byte
mov [di+0ch],ax ; load outregs.x.cflag
pop ax ; get di from stack
mov [di+0ah],ax ; load outregs.x.di
;-------------------------------------------------------------------
pop si ; restore registers
pop di
mov sp,bp ; restore sp
pop bp ; restore user's bp
ret
_parse endp
_TEXT ends ; end code segment
end


View File

@ -0,0 +1,288 @@
.xlist
;
;
; CHKDSK Version 2.0
; Verifies and repairs MS-DOS disk directory.
;REV 1.1 ARR
; 05/21/82 Added rev number
;REV 1.5 NP ARR
; Mod by NANCYP to report on extents
; Mod by AARONR to report volume ID
;REV 2.0 ARR
; Total rewrite for directories
;REV 2.1 ARR
; Added ^C and INT 24H handlers
;REV 2.2 ARR
; INTERNATIONAL support
;REV 2.3 NP
; Mod by NANCYP to use 2.0 system calls
; and accept pathnames as parameters
;REV 2.4 NP
; PRINTF incorporated into CHKDSK
; Modified to run as .EXE file
;REV 3.0 ARR 8/30/83
; Update for vers 2.5 of DOS
; 16 bit FATS
;REV 3.05 RS 10/11/84
; Split into CHKDSK2.ASM for on-machine assembly.
;REV 3.20 RS 9/26/85
; Allow 0F0H as a valid DOS media descriptor byte - used for non-standard
; media layouts.
;
;*****************************************************************************
;* *
;* Change list to CHKDSK modules *
;* *
;* Lines are tagged ANxxx for new, ACxxx for changed *
;* --------------------------------------------------------------------------*
;* 000 - DOS 4.00 Spec additions and DCR's thru unit/function test *
;* Date: 8/3/87 Developer: MT *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 001 - DOS 4.00 PTM P265 - Give 'Can't chkdsk subst drive" when running *
;* hardfile. Using 1 based drive insted of 0 *
;* Date: 8/17/87 Developer: Mark T. *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 002 - DOS 4.00 PTM P251 - Hang when chkdsk default drive. Not setting up *
;* drive fields correctly on default drive *
;* Date: 8/14/87 Developer: Mark T. *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* *
;* *
;* *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 005 - DOS 4.00 DCR D166 - Enable 128k FAT *
;* Date: 8/21/87 Developer: Bruce B. *
;* general modifications are: reserve the rest of the program segment for the*
;* stack, put the fat-table next after the end of the program seg, then *
;* put the fatmap area next after the end of the fat-table. *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 006 - DOS 4.00 ptm p097 - change calculation of total disk space *
;* Date: 8/28/87 Developer: Bruce B. *
;* modules - chkinit.sal, chkdsk2.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 007 - DOS 4.00 ptm p816 - files with length zero *
;* Date: 8/21/87 Developer: Bruce B. *
;* modules - chkproc.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 008 - DOS 4.00 ptm p872 - incorrect media size reported *
;* Date: 9/10/87 Developer: Bruce B. *
;* modules - chkinit.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 009 - DOS 4.00 ptm p1151- incorrect date and time *
;* Date: 9/10/87 Developer: Bruce B. *
;* modules - chkdsk1.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 010 - DOS 4.00 ptm p1158- incorrect disk size when disk is full *
;* Date: 9/10/87 Developer: Bruce B. *
;* modules - chkfat.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 011 - DOS 4.00 ptm p817 - cant check files *
;* Date: 9/24/87 Developer: Bruce B. *
;* modules - chkdsk1.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 012 - DOS 4.00 ptm p1223- month and day reversed *
;* Date: 9/22/87 Developer: Bruce B. *
;* modules - chkdsk1.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 013 - DOS 4.00 ptm p1238- not detect filesize <> number of clusters *
;* Date: 9/25/87 Developer: Bruce B. *
;* modules - chkproc.sal, chkdisk.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* - DOS 4.00 ptm p1239- hangs when file has invalid ??? *
;* Date: 9/25/87 Developer: Bruce B. *
;* modules - chkproc.sal, chkdisk.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 014 - DOS 4.00 ptm p1240- not detect crosslinked files *
;* Date: 9/25/87 Developer: Bruce B. *
;* modules - chkproc.sal, chkfat.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* - DOS 4.00 ptm p1241- hangs when trying to fix lost subdir *
;* Date: 9/25/87 Developer: Bruce B. *
;* modules - chkproc.sal, chkfat.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* - DOS 4.00 ptm p1242- hangs when lost subdir found *
;* Date: 9/25/87 Developer: Bruce B. *
;* modules - chkproc.sal, chkfat.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 015 - DOS 4.00 ptm p1176 - not working for vdisk drives *
;* Date: 10/1/87 Developer: Bruce B. *
;* modules - chkinit.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 016 - DOS 4.00 ptm p1436 - not working for full disk with system files *
;* Date: 10/2/87 Developer: Bruce B. *
;* modules - chkproc.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* - DOS 4.00 ptm p1437 - not working on vdisk *
;* Date: 10/2/87 Developer: Bruce B. *
;* modules - chkproc.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* - DOS 4.00 ptm p1447 - chkdsk filenam --> invalid drive spec *
;* Date: 10/2/87 Developer: Bruce B. *
;* modules - chkproc.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 017 - DOS 4.00 ptm p1491 - invalid use of common msgs *
;* Date: 10/5/87 Developer: Bruce B. *
;* modules - chkdsk.skl chkmsg.inc *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 018 - DOS 4.00 ptm p1507 - 'non_dos' instead of 'non-dos' *
;* Date: 10/6/87 Developer: Bruce B. *
;* modules - chkdsk.skl *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 019 - DOS 4.00 ptm p1506 - '0 bytes would be freed' *
;* Date: 10/6/87 Developer: Bruce B. *
;* modules - *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 020 - DOS 4.00 ptm p1556 - chkdsk allows 2 positional or keyword parms *
;* Date: 10/8/87 Developer: Bruce B. *
;* modules - chkparse.inc *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 021 - DOS 4.00 ptm p1557 - displays invalid drive spec twice *
;* Date: 10/8/87 Developer: Bruce B. *
;* modules - chkinit.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 022 - DOS 4.00 ptm p1558 - divide overflow on invalid drive *
;* Date: 10/8/87 Developer: Bruce B. *
;* modules - chkinit.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 023 - DOS 4.00 ptm p1559 - abnormal results when int13 is bad *
;* Date: 10/8/87 Developer: Bruce B. *
;* modules - *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 024 - DOS 4.00 ptm p1606 - no display of volume serial number *
;* Date: 10/12/87 Developer: Bruce B. *
;* modules - chkdsk2.sal, chkmsg.inc *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 025 - DOS 4.00 ptm p1761 - doesnt work on zerod out cluster for dir *
;* Date: 10/17/87 Developer: Bruce B. *
;* modules - chkproc.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 026 - DOS 4.00 ptm p1842 - chkdsk accepts 2 filespec parms *
;* Date: 10/20/87 Developer: Bruce B. *
;* modules - chkinit.sal, chkparse.inc *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 027 - DOS 4.00 ptm p2007 - test case 7 - chkdsk a: /v (invalid subdirs) *
;* Date: 10/24/87 Developer: Bruce B. *
;* modules - chkproc.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 028 - DOS 4.00 ptm p2029 - chkdsk cant exec for afs *
;* Date: 10/26/87 Developer: Bruce B. *
;* modules - chkexec.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 029 - DOS 4.00 ptm p2104 - chkdsk goes to drive a: on ctl-break *
;* Date: 10/29/87 Developer: Bruce B. *
;* modules - chkfat.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 030 - DOS 4.00 ptm p2323 - low memory check, correct free memory report *
;* Date: 11/04/87 Developer: Bruce B. *
;* modules - chkfat.sal, chkdsk2.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 031 - DOS 4.00 ptm p2495 - incorrect message for drive not ready *
;* Date: 11/17/87 Developer: Bruce B. *
;* modules - chkinit.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 032 - DOS 4.00 ptm p2648 - unformatted disk displays "invalid device type" *
;* Date: 11/24/87 Developer: Bruce B. *
;* modules - chkinit.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 033 - DOS 4.00 ptm p2781 - divide overflow on unformatted diskette *
;* Date: 12/07/87 Developer: Bruce B. *
;* modules - chkinit.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 034 - DOS 4.00 ptm p2975 - get psp done three times *
;* Date: 12/20/87 Developer: Bruce B. *
;* modules - chkinit.sal, chkdsk1.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 035 - DOS 4.00 ptm p3007 - chkdsk reports incorrect memory *
;* Date: 12/28/87 Developer: Bruce B. *
;* modules - chkinit.sal, chkdsk1.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 036 - DOS 4.00 ptm p3028 - include pathgen into pgm *
;* Date: 01/12/88 Developer: Bruce B. *
;* modules - all *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 037 - DOS 4.00 ptm p3129 - chkdsk fails to build *
;* Date: 01/14/88 Developer: Bruce B. *
;* modules - chkdisp.asm *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 038 - DOS 4.00 ptm p3130 - remove AFS from code *
;* Date: 01/14/88 Developer: Bruce B. *
;* modules - chkinit.sal, chkequ.inc, chkexec.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 039 - DOS 4.00 ptm p3360 - correct addressing of ctl-break handling *
;* Date: 02/05/88 Developer: Bruce B. *
;* modules - chkproc2.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 040 - DOS 4.00 ptm p3573 - pathgen parser and msg ret. *
;* Date: 02/19/88 Developer: Bruce B *
;* modules - chkdisp.asm, chkparse.inc *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 041 - DOS 4.00 dcr d490 - change get media id call for same as os/2 1.0 *
;* Date: 02/26/88 Developer: Bruce B *
;* modules - chkdata.inc, chkdsk1.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 042 - DOS 4.00 ptm p3735 - chkdsk prints files to stderr, not stdout *
;* Date: 03/04/88 Developer: Bruce B *
;* modules - chkmsg.inc *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 043 - DOS 4.00 ptm p3708 - chkdsk prints wrong message for network drive *
;* Date: 03/07/88 Developer: Bruce B *
;* modules - chkinit.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 044 - DOS 4.00 ptm p3840 - wrong message for newtork filename *
;* Date: 03/14/88 Developer: Bruce B *
;* modules - chkinit.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 045 - DOS 4.00 ptm p3876 - hang when .. entry erased and /f parameter *
;* Date: 03/15/88 Developer: Bruce B *
;* modules - chkproc.sal, chkdsk2.sal, chkmsg.inc, chkfat.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 046 - DOS 4.00 ptm p3923?- display invalid parm names *
;* Date: 03/21/88 Developer: Bruce B *
;* modules - chkinit.sal, chkmsg.inc *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 047 - private build only- display lost cluster number *
;* Date: 03/24/88 Developer: Bruce B *
;* modules - chkfat.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 048 - DOS 4.00 PTM p4050 - wont recover . and .. entries *
;* Date: 04/12/88 Developer: Bruce B *
;* modules - many *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 049 - DOS 4.00 PTM p4125 - chkdsk prints incorrect user file bytes *
;* Date: 04/13/88 Developer: Bruce B. *
;* modules - many *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 050 - DOS 4.00 PTM p4571 - chkdsk and mem report diff ram under Windows *
;* Date: 05/02/88 Developer: Bruce B. *
;* modules - chkdsk1.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 051 - DOS 4.00 PTM p4571 - chkdsk does not recover lost clusters into files*
;* Date: 05/05/88 Developer: Bruce B. *
;* modules - chkfat.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 052 - DOS 4.00 PTM p4869 - handle MS ramdrive.sys *
;* Date: 05/16/88 Developer: Bruce B. *
;* modules - chkinit.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 053 - DOS 4.00 PTM p4924 - oops! do it right this time.... *
;* Date: 05/19/88 Developer: Bruce B. *
;* modules - chkinit.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 054 - DOS 4.00 PTM p4957 - both chkdsk & mem do avail mem incorrectly *
;* Date: 05/24/88 Developer: Bruce B. *
;* modules - chkdsk1.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* 055 - DOS 4.00 PTM p5007 - wont handle '\' as 2nd byte of dbcs pair *
;* Date: 06/01/88 Developer: Bruce B *
;* modules - chkdsk1.sal, chkinit.sal *
;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
;* *
;*****************************************************************************
;* Note: This is file CHKCHNG.INC for updating purposes *
;*****************************************************************************

View File

@ -0,0 +1,244 @@
CONST SEGMENT PUBLIC PARA 'DATA'
EXTRN STACKMES:byte
EXTRN BADVER:byte, BADDRV_ARG:word, INVPATH_ARG:word
EXTRN FILE_ARG:word
EXTRN BADCD_ARG:word, BADSUBDIR:byte
EXTRN no_mem_arg:word ;an030;bgb
EXTRN BADRDMES:byte
EXTRN BADDRVM:byte
EXTRN BADIDBYT:byte
EXTRN OPNERR_ARG:word, NOEXT_ARG:word, EXTENT_ARG:word
EXTRN IDMES_ARG:WORD
EXTRN ORPH_ARG:WORD
EXTRN FILE_ARG1:WORD, FILE_ARG2:WORD
EXTRN badrw_num:word, BADRW_STR:WORD, BLOCK_NUM:WORD
EXTRN FATAL_ARG1:WORD, FATAL_ARG2:WORD
EXTRN FATmsg2:word ;an024;bgb
EXTRN BADSW_ARG:WORD, DSKSPC:WORD ;an049;bgb
EXTRN HIDMES:WORD, DIRMES:WORD, FILEMES:WORD, ORPHMES2:WORD
EXTRN ORPHMES3:WORD, BADSPC:WORD, FRESPC:WORD
EXTRN FREMEM:WORD, REPORT_ARG:WORD, CRLF_ARG:WORD
EXTRN RARG1:WORD, RARG3:WORD, ORPHCNT:WORD
EXTRN NO_NET_ARG:byte, MONTAB:BYTE, SubstErr:BYTE
EXTRN ExitStatus:Byte,Badr_Arg:Byte ;an000;bgb
EXTRN Sublist_msg_Idmes:word ;an000;bgb
extrn msgserialnumber:byte ;an000;bgb
extrn psp_segment:word ;an000;bgb;an034;bgb
;an000;bgb
PUBLIC SWITCHAR
PUBLIC TCHAR
PUBLIC HECODE
PUBLIC conbuf
PUBLIC DOTMES
PUBLIC NOISY
PUBLIC DOTENT
PUBLIC HAVFIX
PUBLIC DOFIX
PUBLIC DIRBUF
PUBLIC PARSTR, DDOTENT, NUL, ERRSUB, SECONDPASS, ALLFILE
PUBLIC ORPHFCB, ORPHEXT, HIDCNT, HIDSIZ, FILCNT, FILSIZ, DIRCNT
PUBLIC DIRSIZ, DIRTYFAT, CROSSCNT, BADSIZ, ORPHSIZ, LCLUS
PUBLIC USERDIR, FRAGMENT, ALLDRV, FIXMFLG, DIRCHAR
PUBLIC BIGFAT, EOFVAL, BADVAL,CHAIN_END
PUBLIC fTrunc,Volnam
PUBLIC temp_dd ;an049;bgb
DIRBUF LABEL BYTE ;Entry buffer for searches
VOLID DB -1,0,0,0,0,0,8 ;Volume ID FCB
VOLNAM DB 0,"???????????"
DB 25 DUP(0)
ALLFILE DB -1 ;Extended FCB indicator
DB 0,0,0,0,0 ;reserved bytes
DB 1EH ;attribute byte 0001-1110 hidden, system, label, subdir
ALLDRV DB 0 ;default drive
DB "???????????" ;any file name
DB 25 DUP (?)
ORPHFCB DB 0,"FILE0000"
ORPHEXT DB "CHK"
DB 25 DUP (?)
fcb_copy db 32 dup (?)
;Non-message data
pFileName DW ? ; pointer
SWITCHAR DB "/"
ROOTSTR LABEL BYTE ;use this to change dir to the root
DIRCHAR DB "\"
NUL DB 0
PARSTR DB "..",0
DOTMES DB ".",0
DOTENT DB ". "
DDOTENT DB ".. "
HECODE DB ?
FIXMFLG DB 0 ;Flag for printing fixmes
ERRSUB DW 0 ;Flag for bad subdir error
FRAGMENT DB 0 ;Flag for extent processing
DIR_FIX DB 0 ;Flag for changing dir back to users'
DIRTYFAT DB 0 ;Dirty flag for FAT
;
;note - all these fields that count allocation units can remain the same,
; because the total au's are always less than 64k (1 word).
; looks like the number of files and directories should change, though.
DIRCNT dd 0 ;# directories ;an049;bgb
DIRSIZ dw 0 ;# alloc units in dirs ;an049;bgb
FILCNT dd 0 ;# reg files
FILSIZ dw 0 ;# alloc units in reg files
HIDCNT dd 0 ;# hidden files
HIDSIZ dw 0 ;# alloc units in hid files
BADSIZ dw 0 ;# alloc units in bad sectors
ORPHSIZ dw 0 ;# alloc units in orphan files
LCLUS dw 0 ;# alloc units in lost clusters
DISPFLG DB 0 ;used by number routines
CROSSCNT dd 0 ;# crosslinked files (first pass)
;end of display fields
;
temp_dd dd 0 ;temporary double word field for orphcnt;an049;bgb
SECONDPASS DB 0 ;Pass flag
HAVFIX DB 0 ;non zero if any fixes
DOFIX DB 0 ;flag for F switch
NOISY DB 0 ;flag for V switch
BIGFAT DB 0 ;0=12 bit FAT, NZ=16bit FAT
EOFVAL DW 0FF8H ;0FF8 for 12 bit FAT,0FFF8 for 16 bit
CHAIN_END DW 0FFFH ;0FFF for 12 bit FAT,0FFFF for 16 bit ;AN000;
BADVAL DW 0FF7H ;0FF7 for 12 bit FAT,0FFF7 for 16 bit
mon_name db 3 dup (?),0
TCHAR DB 'a'
USERDIR DB "\",0 ;Users current dir for drive
DB (DIRSTRLEN-1) DUP (?)
CONBUF DB 15,0 ;Input buffer
DB 15 DUP (?)
fTrunc DB FALSE ; TRUE => couldn't chdir, no freeing.
badread db " File allocation table bad",0
CONST ENDS
DATA SEGMENT PUBLIC PARA 'DATA'
PUBLIC THISDPB,DOTSNOGOOD,NUL_ARG,STACKLIM,ZEROTRUNC
PUBLIC NAMBUF,SRFCBPT,fatmap,ISCROSS,MCLUS,CSIZE,SSIZE
PUBLIC DSIZE,ARG1,ARG_BUF,ERRCNT,USERDEV,SECBUF
PUBLIC HARDCH,CONTCH,PATH_NAME,TMP_SPC,mem_size
public Read_Write_Relative,Transrc, fatcnt, fattbl_seg ;an000;bgb
public firstfat, fatsiz, secs_per_64k, paras_per_fat, sec_count ;an000;bgb
public firstsec ;an047;bgb
public dirsec ;an047;bgb
public root_entries ;an047;bgb
public paras_per_64k, save_drive ;an000;bgb
public sernum ;an000;bgb;an024;bgb
ifdef fsexec ;an038;bgb
public exec_path ;an038;bgb;an000;bgb;an027;bgb
public exec_block ;an038;bgb;an000;bgb;an027;bgb
public path_string ;an038;bgb;an000;bgb;an027;bgb
endif ;an038;bgb
public end_of_fatmap ;an000;bgb;an030;bgb
public DBCS_VECTOR ;an055;bgb
public DBCS_VECTOR_off ;an055;bgb
public DBCS_VECTOR_seg ;an055;bgb
DBCS_VECTOR DB 0
DBCS_VECTOR_off dw 0
DBCS_VECTOR_seg dw 0
ifdef fsexec ;an038;bgb
Exec_Block Exec_Block_Parms <> ;an038;bgb;an027;bgb
EXEC_Path db 66 dup(0) ;an038;bgb;an027;bgb
;These next two should stay togather ;an027;bgb
; --------------------------------------- ;an027;bgb
Path_String db "PATH=" ; ;an027;bgb
Len_Path_String equ $ - Path_String ; ;an027;bgb;AN000;
;---------------------------------------- ;an027;bgb
endif ;an038;bgb
;an038;bgb;an027;bgb
;an027;bgb
;These should stay togather ;an027;bgb
; --------------------------------------- ;an027;bgb
; ;an027;bgb
Search_Chkdsk db "KSDKHC" ; ;an027;bgb
Len_Search_Chkdsk equ $ - Search_Chkdsk ; ;an027;bgb
Search_Chkdsk_End equ $-1 ;an027;bgb
; ;an027;bgb
;---------------------------------------- ;an027;bgb
save_drive db 0 ;determines whether drive specified is valid
firstfat dw 0 ;sector number of fat ;an005;bgb
firstsec dw 0 ;sector number of data area ;an047;bgb
dirsec dw 0 ;sector number of dir area ;an047;bgb
root_entries dw 0 ;number of entries in root dir ;an047;bgb
fattbl_seg dw 0 ;segment of the fat-table ;an005;bgb
sec_count dw 0 ;sectors / 64k
secs_per_64k dw 0 ;an005;bgb
paras_per_64k dw 0 ;an005;bgb
fatsiz dw 0 ;an005;bgb
paras_per_fat dw 0 ;an005;bgb
fatcnt db 2 ;number of fats on disk ;an005;bgb
HARDCH dd ? ;Pointer to real INT 24 handler
CONTCH DD ? ;Pointer to real INT 23 handler
THISDPB DD ? ;Pointer to drive DPB
USERDEV DB ? ;Users current device
CSIZE DB ? ;Sectors per cluster 1-256
SSIZE DW ? ;bytes per sector 1-64k
DSIZE DW ? ;# alloc units on disk
MCLUS DW ? ;DSIZE + 1
NAMBUF DB 14 DUP (?) ;Buffer
DOTSNOGOOD DB ? ;. or .. error flag
ZEROTRUNC DB ? ;Trimming flag
ISCROSS DB ? ;Crosslink flag
OLDCLUS DW ?
SRFCBPT DW ?
fatmap DW ? ;segment of fatmap table ;an005;bgb
end_of_fatmap dw ? ;last mem segment used ;an030;bgb
SECBUF DW ? ;Offset of sector buffer (in ram)
ERRCNT DB ? ;Used by FATread and write
PATH_NAME DB 128 DUP(0)
FNAME_LEN DW 128
NUL_ARG DB ?
ARG1 DW ?
ARG2 DW ?
ARG3 DW ?
;
; The following is used as a PRINTF buffer and also as the source/destination
; for a name trans
;
ARG_BUF DB 256 DUP (?)
TMP_SPC DB 128 DUP (?)
mon dw ?
day dw ?
year dw ?
mem_size dw ?
;;;TRANSRC DB "A:CON",0,0 ; Device so we don't hit the drive
TRANSRC DB "A:\",0,0 ; Device so we don't hit the drive
Read_Write_Relative Relative_Sector_Buffer <> ; ;AN000;
STACKLIM DW ? ;Stack growth limit
INTERNATVARS internat_block <>
DB (internat_block_max - ($ - INTERNATVARS)) DUP (?)
; Structure for Get_Media_Id ;an024;bgb
SerNumBuf Label Byte ;AN000;S GENERIC_IOCTL buffer ;an024;bgb
dw 0 ;AN000;S Info level (set on input) ;an024;bgb
SerNum dd 0 ;AN000;S Serial # ;an024;bgb
db 11 DUP(' ') ;AN000;S Volume label ;an024;bgb
db 8 DUP(' ') ;AN000;S File system type ;an024;bgb
DATA ENDS
;an000;bgb
;an000;bgb
lastseg SEGMENT PUBLIC PARA 'LAST' ;an000;bgb
public fattbl ;an000;bgb
fattbl db 0 ;this is the last thing in the pgm ;an000;bgb;an005;bgb
lastseg ends ;this is where the fat is put in ram ;an000;bgb

View File

@ -0,0 +1,328 @@
TITLE CHKDISK - procedures that read or write to the disk
page ,132 ;
.xlist
include chkseg.inc ;an005;bgb
INCLUDE CHKCHNG.INC
INCLUDE DOSSYM.INC
INCLUDE CHKEQU.INC
INCLUDE CHKMACRO.INC
include pathmac.inc
CONST SEGMENT PUBLIC PARA 'DATA'
EXTRN FIXMES_ARG:word
EXTRN BADW_ARG:word
EXTRN badrw_num:word,BADRW_STR:WORD,HAVFIX:byte
EXTRN DIRTYFAT:byte,DOFIX:byte,SECONDPASS:byte
EXTRN HECODE:byte,USERDIR:byte,FRAGMENT:byte
EXTRN ORPHEXT:byte,ALLDRV:byte,FIXMFLG:byte,DIRCHAR:byte
EXTRN EOFVAL:word,BADVAL:word
extrn fTrunc:BYTE
CONST ENDS
DATA SEGMENT PUBLIC PARA 'DATA'
EXTRN THISDPB:dword,NUL_ARG:byte
EXTRN NAMBUF:byte,SRFCBPT:word,FATMAP:word
EXTRN USERDEV:byte,HARDCH:dword,CONTCH:dword
EXTRN ExitStatus:Byte,Read_Write_Relative:Byte
extrn bytes_per_sector:word ;an005;bgb
extrn sec_count:word, paras_per_64k:word, secs_per_64k:word ;an005;bgb
extrn fattbl_seg:word, paras_per_fat:word ;an005;bgb
DATA ENDS
CODE SEGMENT PUBLIC PARA 'CODE'
ASSUME CS:DG,DS:DG,ES:DG,SS:DG
EXTRN FCB_TO_ASCZ:NEAR
EXTRN EPRINT:NEAR
EXTRN PROMPTYN:NEAR,DIRPROC:NEAR
EXTRN DOCRLF:NEAR,UNPACK:NEAR,PACK:NEAR
EXTRN CHECKNOFMES:NEAR
public read_disk, Read_once, write_disk, Write_once ;an005;bgb
public ReadFt, seg_adj, calc_sp64k ;an005;bgb
.list
pathlabl chkdisk
;========================================================================= ;an005;bgb
; READ_DISK : This routine reads the logical sector count requested. ;an005;bgb
; It will read a maximum of 64k in one read. If more ;an005;bgb
; than 64k exists it will continue looping until ;an005;bgb
; all sectors have been read. ;an005;bgb
; ;an005;bgb
; Inputs : AL - Drive letter ;an005;bgb
; ES:BX - Segment:offset of transfer address ;an005;bgb
; CX - Sector count ;an005;bgb
; DX - 1st sector ;an005;bgb
; ;an005;bgb
; Outputs : Logical sectors read ;an005;bgb
; LOGIC ;an005;bgb
; ***** ;an005;bgb
; adjust es:bx to es:00 ;an005;bgb
; calcluate sectors-per-64k (how many sectors are there that can fit within a 64k segment?)
; DO while there are more sectors to read than sectors-per-64k ;an005;bgb
; set sector-count to sectors-per-64k ;an005;bgb
; perform the disk read ;an005;bgb
; bump the seg addr to the new addr ;an005;bgb
; dec the number of sectors to read by sectors-per-64k ;an005;bgb
; bump the starting sector number by the sectors-per-64k ;an005;bgb
; ENDDO ;an005;bgb
; perform a disk read for less than sectors-per-64k ;an005;bgb
;========================================================================= ;an005;bgb
procedure read_disk ;an005;bgb
savereg <ax,bx,cx,dx,es> ;an005;bgb
call seg_adj ;an000;calc new seg:off ;an005;bgb
call calc_sp64k ;an000;secs/64k ;an005;bgb
; $DO ; do while more than 64k ;an005;bgb
$$DO1:
cmp cx,secs_per_64k ;an000;exceed 64k ;an005;bgb
; $LEAVE LE ;an000;yes ;an005;bgb
JLE $$EN1
mov sec_count,cx ;an000;save cx ;an005;bgb
mov cx,secs_per_64k ;an000;get maximum read ;an005;bgb
call read_once ;an000;read it ;an005;bgb
; $LEAVE C ;an005;bgb
JC $$EN1
mov cx,es ;an005;bgb
add cx,paras_per_64k ; adjust transfer area ;an005;bgb
mov es,cx ;an005;bgb
mov cx,sec_count ; restore sector count ;an005;bgb
sub cx,secs_per_64k ;an000;get sectors remaining ;an005;bgb
add dx,secs_per_64k ;an000;adjust starting sector ;an005;bgb
; $ENDDO ;an005;bgb
JMP SHORT $$DO1
$$EN1:
call read_once ;an000;read it ;an005;bgb
restorereg <es,dx,cx,bx,ax> ;an005;bgb
ret ;an005;bgb
read_disk endp ;an005;bgb
;an005;bgb
;an005;bgb
;***************************************************************************** ;an005;bgb
;Routine name: Read_once ;an005;bgb
;***************************************************************************** ;an005;bgb
; ;an005;bgb
;description: Read in data using Generic IOCtl ;an005;bgb
; ;an005;bgb
;Called Procedures: None ;an005;bgb
; ;an005;bgb
; ;an005;bgb
;Change History: Created 5/13/87 MT ;an005;bgb
; ;an005;bgb
;Input: AL = Drive number (0=A) ;an005;bgb
; es:BX = Transfer address ;an005;bgb
; CX = Number of sectors ;an005;bgb
; Read_Write_Relative.Start_Sector_High = Number of sectors high ;an005;bgb
; DX = logical sector number low ;an005;bgb
; ;an005;bgb
;Output: CY if error ;an005;bgb
; AH = INT 25h error code ;an005;bgb
; ;an005;bgb
;Psuedocode ;an005;bgb
;---------- ;an005;bgb
; Save registers ;an005;bgb
; Setup structure for function call ;an005;bgb
; Read the disk (AX=440Dh, CL = 6Fh) ;an005;bgb
; Restore registers ;an005;bgb
; ret ;an005;bgb
;***************************************************************************** ;an005;bgb
Procedure Read_once ; ;an005;bgb
savereg <ax,bx,cx,dx,si,di,bp,es,ds> ;Change it to Read relative sect;an005;bgb
mov Read_Write_Relative.Buffer_Offset,bx ;Get transfer buffer add ;an005;bgb
mov bx,es ; ;AN005;bgb
mov Read_Write_Relative.Buffer_Segment,bx ;Get segment ;an005;bgb
mov Read_Write_Relative.Number_Sectors,cx ;Number of sec to read ;an005;bgb
mov Read_Write_Relative.Start_Sector_Low,dx ;Start sector ;an005;bgb
mov bx,offset Read_Write_Relative ; ;an005;bgb
mov cx,0FFFFh ;Read relative sector ;an005;bgb
INT 25h ;Do the read ;an005;bgb
pop dx ;Throw away flags on stack ;an005;bgb
restorereg <ds,es,bp,di,si,dx,cx,bx,ax> ;an005;bgb
return ;an005;bgb
Read_once endp ;an005;bgb
;an005;bgb
;an005;bgb
;========================================================================= ;an005;bgb
; WRITE-DISK : This routine reads the logical sector count requested. ;an005;bgb
; It will read a maximum of 64k in one read. If more ;an005;bgb
; than 64k exists it will continue looping until ;an005;bgb
; all sectors have been read. ;an005;bgb
; ;an005;bgb
; Inputs : AL - Drive letter ;an005;bgb
; ES:BX - Segment:offset of transfer address ;an005;bgb
; CX - Sector count ;an005;bgb
; DX - 1st sector ;an005;bgb
; ;an005;bgb
; Outputs : Logical sectors read ;an005;bgb
; LOGIC ;an005;bgb
; ***** ;an005;bgb
; adjust es:bx to es:00 ;an005;bgb
; calcluate sectors-per-64k (how many sectors are there that can fit within a 64k segment?)
; DO while there are more sectors to read than sectors-per-64k ;an005;bgb
; set sector-count to sectors-per-64k ;an005;bgb
; perform the disk read ;an005;bgb
; bump the seg addr to the new addr ;an005;bgb
; dec the number of sectors to read by sectors-per-64k ;an005;bgb
; bump the starting sector number by the sectors-per-64k ;an005;bgb
; ENDDO ;an005;bgb
; perform a disk read for less than sectors-per-64k ;an005;bgb
;========================================================================= ;an005;bgb
procedure write_disk ;an005;bgb
savereg <ax,bx,cx,dx,es> ;an013;bgb
call seg_adj ;an000;calc new seg:off ;an005;bgb
; $DO ; do while more than 64k ;an005;bgb
$$DO5:
cmp cx,secs_per_64k ;an000;exceed 64k ;an005;bgb
; $LEAVE LE ;an000;yes ;an005;bgb
JLE $$EN5
mov sec_count,cx ;an000;save cx ;an005;bgb
mov cx,secs_per_64k ;an000;get maximum read ;an005;bgb
call write_once ;an000;read it ;an005;bgb
; $LEAVE C ;an005;bgb
JC $$EN5
mov cx,es ;an005;bgb
add cx,paras_per_64k ; adjust transfer area ;an005;bgb
mov es,cx ;an005;bgb
mov cx,sec_count ; restore sector count ;an005;bgb
sub cx,secs_per_64k ;an000;get sectors remaining ;an005;bgb
add dx,secs_per_64k ;an000;adjust starting sector ;an005;bgb
; $ENDDO ;an005;bgb
JMP SHORT $$DO5
$$EN5:
call write_once ;an000;read it ;an005;bgb
restorereg <es,dx,cx,bx,ax> ;an013;bgb
ret ;an005;bgb
write_disk endp ;an005;bgb
;an005;bgb
;***************************************************************************** ;an005;bgb
;Routine name: Write_once ;an005;bgb
;***************************************************************************** ;an005;bgb
; ;an005;bgb
;description: Write Data using int 26 ;an005;bgb
; ;an005;bgb
;Called Procedures: None ;an005;bgb
; ;an005;bgb
; ;an005;bgb
;Change History: Created 5/13/87 MT ;an005;bgb
; ;an005;bgb
;Input: AL = Drive number (0=A) ;an005;bgb
; DS:BX = Transfer address ;an005;bgb
; CX = Number of sectors ;an005;bgb
; Read_Write_Relative.Start_Sector_High = already set up ;an048;bgb
; DX = logical sector number low ;an005;bgb
; ;an005;bgb
;Output: CY if error ;an005;bgb
; AH = INT 26h error code ;an005;bgb
; ;an005;bgb
;Psuedocode ;an005;bgb
;---------- ;an005;bgb
; Save registers ;an005;bgb
; Setup structure for function call ;an005;bgb
; Write to disk (AX=440Dh, CL = 4Fh) ;an005;bgb
; Restore registers ;an005;bgb
; ret ;an005;bgb
;***************************************************************************** ;an005;bgb
Procedure Write_once ; ;an005;bgb
savereg <ax,bx,cx,dx,di,si,bp,es,ds> ;This is setup for INT 26h right;AN005;bgb
mov Read_Write_Relative.Buffer_Offset,bx ;Get transfer buffer add ;AN005;bgb
mov bx,es ; ;AN005;bgb
mov Read_Write_Relative.Buffer_Segment,bx ;Get segment ;AN005;bgb
mov Read_Write_Relative.Number_Sectors,cx ;Number of sec to write ;AN005;bgb
mov Read_Write_Relative.Start_Sector_Low,dx ;Start sector ;AN005;bgb
mov cx,0FFFFh ;Write relative sector ;AN005;bgb
lea bx,read_write_relative ; ;an005;bgb
INT 026h ;Do the write ;AN005;bgb
pop dx ;flags is returned on the stack;AN005;bgb
restorereg <ds,es,bp,si,di,dx,cx,bx,ax> ; ;AN005;bgb
ret ; ;AN005;bgb
Write_once endp ; ;AN005;bgb
;an005;bgb
;========================================================================= ;an005;bgb
; SEG_ADJ : This routine adjusts the segment:offset to prevent ;an005;bgb
; address wrap. ;an005;bgb
; ;an005;bgb
; Inputs : bx - Offset to adjust segment with ;an005;bgb
; es - Segment to be adjusted ;an005;bgb
; ;an005;bgb
; Outputs : bx - New offset ;an005;bgb
; es - Adjusted segment ;an005;bgb
;========================================================================= ;an005;bgb
procedure seg_adj ;an005;bgb
savereg <ax,cx,dx> ;an005;bgb
mov ax,bx ;an000;get offset ;an005;bgb
mov bx,0010h ;divide by 16 ;an005;bgb
xor dx,dx ;an000;clear dx ;an005;bgb
div bx ;an000;get para count ;an022;bgb
mov bx,es ;an000;get seg ;an005;bgb
add bx,ax ;an000;adjust for paras ;an005;bgb
mov es,bx ;an000;save new seg ;an005;bgb
mov bx,dx ;an000;new offset ;an005;bgb
restorereg <dx,cx,ax> ;an005;bgb
ret ;an005;bgb
seg_adj endp ;an005;bgb
;an005;bgb
;an005;bgb
;========================================================================= ;an005;bgb
; CALC_SP64K : This routine calculates how many sectors, for this ;an005;bgb
; particular media, will fit into 64k. ;an005;bgb
; ;an005;bgb
; Inputs : DPB_SECTOR_SIZE - bytes/sector ;an005;bgb
; ;an005;bgb
; Outputs : SECS_PER_64K - Sectors / 64k ;an005;bgb
; PARAS_PER_64K - paragraphs per 64k ;an005;bgb
;========================================================================= ;an005;bgb
procedure calc_sp64k ;an005;bgb
savereg <ax,bx,cx,dx> ;an005;bgb
mov ax,0ffffh ;an000;64k ;an005;bgb
mov bx,bytes_per_sector ;an000;get bytes/sector ;an005;bgb
xor dx,dx ;an000;clear dx ;an005;bgb
div bx ;an000;sector count ;an022;bgb;bgb
mov secs_per_64k,ax ;an000;save sector count ;an005;bgb
mov ax,bytes_per_sector ;an000;get bytes/sector ;an005;bgb
mov bx,010h ; divide by paras ;an005;bgb
xor dx,dx ;an000;clear dx ;an005;bgb
div bx ; paras per sector ;an022;bgb;bgb
mul secs_per_64k ; times sectors ;an005;bgb
mov paras_per_64k,ax ; = paras per 64k ;an005;bgb
restorereg <dx,cx,bx,ax> ;an000;restore dx ;an005;bgb
ret ;an000; ;an005;bgb
calc_sp64k endp ;an000; ;an005;bgb
;an005;bgb
;an005;bgb
Break <ReadFT - read in the entire fat> ;an005;bgb
;****************************************************************************** ;an005;bgb
; ReadFt - attempt to read in the fat. If there are errors, step to ;an005;bgb
; successive fats until no more. ;an005;bgb
; ;an005;bgb
; Inputs: none. ;an005;bgb
; Outputs: Fats are read until one succeeds. ;an005;bgb
; Carry set indicates no Fat could be read. ;an005;bgb
; Registers modified: all ;an005;bgb
; LOGIC ;an005;bgb
; ***** ;an005;bgb
; DO for each of the fats on the disk: ;an005;bgb
; read - all the sectors in the fat ;an005;bgb
; increase the starting sector by the number of sectors in each fat ;an005;bgb
; ;an005;bgb
; LARGE FAT SUPPORT - the big change here is in read disk. since the fat must ;an005;bgb
; be within the first 32M, then the starting sector number of 65535 is ok, ;an005;bgb
; as is a larger number of sectors to read/write. ;an005;bgb
;****************************************************************************** ;an005;bgb
Procedure ReadFt,NEAR ;an005;bgb
clc ;Clear CY so we will loop ;an005;bgb
mov Read_Write_Relative.Start_Sector_High,0 ; ;an005;bgb
call Read_Disk ; Read_Disk (); ;AC0;an005;bgb
; $IF C
JNC $$IF9
add dx,cx ; fatstart += fatsize ;an005;bgb
call Read_Disk ; Read_Disk (); ;AC0;an005;bgb
; $ENDIF
$$IF9:
bad_read: ret ;an005;bgb
EndProc ReadFt ;an005;bgb
pathlabl chkdisk
CODE ENDS
END


View File

@ -0,0 +1,139 @@
page ,132 ; ;an000;bgb
;***************************************************************************** ;an000;bgb
;***************************************************************************** ;an000;bgb
;UTILITY NAME: FORMAT.COM ;an000;bgb
; ;an000;bgb
;MODULE NAME: DISPLAY.ASM ;an000;bgb
; ;an000;bgb
; ;an000;bgb
; Designed: Mark T. ;an000;bgb
; ;an000;bgb
; Change List: AN000 - New code DOS 3.3 spec additions ;an000;bgb
; AC000 - Changed code DOS 3.3 spec additions ;an000;bgb
;***************************************************************************** ;an000;bgb
;an000;bgb
EXTRN command_line_buffer:byte ;an000;bgb;an005;bgb
;***************************************************************************** ;an000;bgb
; Include Files ;an000;bgb
;***************************************************************************** ;an000;bgb
.xlist ;an000;bgb
include pathmac.inc ;an040;bgb
include chkseg.inc ;an000;bgb
INCLUDE CPMFCB.INC ;an000;bgb
INCLUDE CHKEQU.INC ;an000;bgb
.list ;an000;bgb
INCLUDE CHKMSG.INC ;an000;bgb
.xlist ;an000;bgb
INCLUDE SYSMSG.INC ;an000;bgb
.list ;an000;bgb
; ;an000;bgb
cstack segment para stack 'STACK' ;an000;bgb
db 62 dup ("-Stack!-") ; (362-80h) is the additional IBM ROM ;an000;bgb
cstack ends ;an000;bgb
;an000;bgb
;an000;bgb
;***************************************************************************** ;an000;bgb
; Message Services ;an000;bgb
;***************************************************************************** ;an000;bgb
MSG_UTILNAME <CHKDSK> ;an000;bgb
;an000;bgb
;.xlist ;an000;bgb
data segment public para 'DATA' ;an000;bgb
Msg_Services <MSGDATA> ;an000;bgb
data ends ;an000;bgb
;an000;bgb
code segment public para 'CODE' ;an000;bgb
pathlabl msgret ;an040;bgb
Msg_Services <NEARmsg> ;an000;bgb
Msg_Services <LOADmsg> ;an000;bgb
Msg_Services <DISPLAYmsg,CHARmsg,NUMmsg,TIMEmsg,DATEmsg> ;an000;bgb
pathlabl msgret ;an040;bgb
Msg_Services <CHKDSK.CLA,CHKDSK.CLB,CHKDSK.CLC,CHKDSK.CLD,CHKDSK.CL1,CHKDSK.CL2,CHKDSK.CTL> ;an037;bgb
code ends ;an000;bgb
.list ;an000;bgb
;an000;bgb
; ;an000;bgb
;***************************************************************************** ;an000;bgb
; Public Declarations ;an000;bgb
;***************************************************************************** ;an000;bgb
Public SysLoadMsg ;an000;bgb
Public SysDispMsg ;an000;bgb
;an000;bgb
;an000;bgb
; ;an000;bgb
;*************************************************************************** ;an000;bgb
; Message Structures ;an000;bgb
;*************************************************************************** ;an000;bgb
Message_Table struc ; ;an000;bgb;AN000;
Entry1 dw 0 ; ;an000;bgb;AN000;
Entry2 dw 0 ; ;an000;bgb;AN000;
Entry3 dw 0 ; ;an000;bgb;AN000;
Entry4 dw 0 ; ;an000;bgb;AN000;
Entry5 db 0 ; ;an000;bgb;AN000;
Entry6 db 0 ; ;an000;bgb;AN000;
Entry7 dw 0 ; ;an000;bgb;AN000;
Message_Table ends ; ;an000;bgb;AN000;
;an000;bgb
code segment public para 'CODE' ; ;an000;bgb;AN000;
;***************************************************************************** ;an000;bgb
;Routine name&gml Display_Interface ;an000;bgb
;***************************************************************************** ;an000;bgb
; ;an000;bgb
;DescriptioN&gml Save all registers, set up registers required for SysDispMsg ;an000;bgb
; routine. This information is contained in a message description ;an000;bgb
; table pointed to by the DX register. Call SysDispMsg, then ;an000;bgb
; restore registers. This routine assumes that the only time an ;an000;bgb
; error will be returned is if an extended error message was ;an000;bgb
; requested, so it will ignore error returns ;an000;bgb
; ;an000;bgb
;Called Procedures: Message (macro) ;an000;bgb
; ;an000;bgb
;Change History&gml Created 4/22/87 MT ;an000;bgb
; ;an000;bgb
;Input&gml ES&gmlDX = pointer to message description ;an000;bgb
; ;an000;bgb
;Output&gml None ;an000;bgb
; ;an000;bgb
;Psuedocode ;an000;bgb
;---------- ;an000;bgb
; ;an000;bgb
; Save all registers ;an000;bgb
; Setup registers for SysDispMsg from Message Description Tables ;an000;bgb
; CALL SysDispMsg ;an000;bgb
; Restore registers ;an000;bgb
; ret ;an000;bgb
;***************************************************************************** ;an000;bgb
Public Display_Interface ;an000;bgb
Display_Interface proc ; ;an000;bgb;AN000;
push ds ;an000;bgb
push ax ;an000;bgb
push bx ;an000;bgb
push cx ;an000;bgb
push dx ;an000;bgb
push si ;an000;bgb
push di ;an000;bgb
mov di,dx ;Change pointer to table ;an000;bgb;AN000;
mov dx,dg ;Point to group ;an000;bgb
mov ds,dx ; ;an000;bgb
mov ax,[di].Entry1 ;Message number ;an000;bgb;AN000;
mov bx,[di].Entry2 ;Handle ;an000;bgb;AN000;
mov si,[di].Entry3 ;Sublist ;an000;bgb;AN000;
mov cx,[di].Entry4 ;Count ;an000;bgb;AN000;
mov dh,[di].Entry5 ;Class ;an000;bgb;AN000;
mov dl,[di].Entry6 ;Function ;an000;bgb;AN000;
mov di,[di].Entry7 ;Input ;an000;bgb;AN000;
call SysDispMsg ;Display the message ;an000;bgb;AN000;
pop di ;an000;bgb
pop si ;an000;bgb
pop dx ;an000;bgb
pop cx ;an000;bgb
pop bx ;an000;bgb
pop ax ;an000;bgb
pop ds ;an000;bgb
ret ;All done ;an000;bgb;AN000;
Display_Interface endp ; ;an000;bgb;AN000;
;an000;bgb
include msgdcl.inc
code ends ;an000;bgb
end ;an000;bgb

View File

@ -0,0 +1,7 @@
CHKDSK1.ASM
CHKMES.ASM
CHKPRMT.ASM
CHKPROC.ASM
CHKPROC2.ASM
CHKDSK2.ASM


View File

@ -0,0 +1,12 @@
chkdisk+
chkdisp+
CHKDSK1+
CHKDSK2+
chkfat+
CHKINIT+
CHKPRMT+
CHKPROC2+
CHKPROC
CHKDSK.EXE,CHKDSK.MAP ;
;chkexec+ ;an038;bgb


View File

@ -0,0 +1,82 @@
:util CHKDSK ;an000;bgb
;an000;bgb
:class A ;an000;bgb
:use COMMON1 ;Incorrect DOS version ;an000;bgb
:use COMMON2 ;stackmes ;an000;bgb
:def 3 "Convert lost chains to files (Y/N)?" ;freemes ;an000;bgb
:def 4 "Unrecoverable error in directory" ;ptrandir ;an000;bgb
:def 5 "Convert directory to file (Y/N)?" ;ptrandir2 ;an000;bgb
:def 7 "%1 bytes total disk space" ;dskspc ;an000;bgb
:def 8 "%1 bytes in bad sectors" ;badspc ;an000;bgb
:def 9 "%1 bytes in %2 hidden files" ;hidmes ;an000;bgb
:def 10 "%1 bytes in %2 directories" ;dirmes ;an000;bgb
:def 11 "%1 bytes in %2 user files" ;filemes ;an000;bgb
:def 12 "%1 bytes in %2 recovered files" ;orphmes2 ;an000;bgb
:def 13 "%1 bytes would be in %2 recovered files" ;orphmes3 ;an000;bgb
:def 14 "%1 bytes available on disk" ;frespc ;an000;bgb
:def 15 "%1 total bytes memory" ;totmem ;an000;bgb
:def 16 "%1 bytes free" ;fremem ;an000;bgb
:def 17 "Cannot CHKDSK a network drive" ;no_net_arg ;an000;bgb
:def 18 "Cannot CHKDSK a SUBSTed or ASSIGNed drive" ;SubStErr ;an000;bgb
:def 19 "Probable non-DOS disk",CR,LF,"Continue (Y/N)?" ;badidbyt ;an018;bgb ;an000;bgb
:def 20 "Disk error reading FAT %1",CR,LF ;badr ;an000;bgb
;an000;bgb
:class B ;an000;bgb
:def 21 "Directory %1" ;direc_arg ;an000;bgb
:def 22 "%1 Contains %2 non-contiguous blocks" ;extent_arg ;an000;bgb
:def 23 "All specified file(s) are contiguous" ;noext_arg ;an000;bgb
:def 24 "Errors found, F parameter not specified",CR,LF,"Corrections will not be written to disk" ;fixmes_arg;an000;bgb
:def 25 " Processing cannot continue %1%2" ;fatal_arg ;an000;bgb
:def 26 " File allocation table bad, drive %1" ;badrdmes ;an000;bgb
:use COMMON2 ;stackmes ;an000;bgb
:def 29 " CHDIR .. failed, trying alternate method" ;cdddmes ;an000;bgb
:def 30 " Has invalid cluster, file truncated" ;badchain ;an000;bgb
:def 31 " Invalid sub-directory entry" ;badsubdir ;an000;bgb
:def 32 " Does not exist" ;ndotmes ;an000;bgb
:def 33 " First cluster number is invalid, entry truncated" ;nulnz ;an000;bgb
:def 34 " Allocation error, size adjusted" ;badclus ;an000;bgb
:def 35 " Cannot recover .. entry, processing continued" ;norecdot ;an000;bgb
:def 36 " Directory is totally empty, no . or .." ;nuldmes ;an000;bgb
:def 37 " Directory is joined" ;joinmes ;an000;bgb
:def 38 " Cannot recover .. entry" ;norecddot ;an000;bgb
:def 39 " Entry has a bad link" ;norecddot1 ;an000;bgb
:def 40 " Entry has a bad attribute" ;norecddot2 ;an000;bgb
;an000;bgb
:class C ;an000;bgb
:def 41 " Entry has a bad size" ;norecddot3 ;an000;bgb
:def 42 " Is cross linked on cluster %1" ;cross_arg ;an000;bgb
:def 43 " Cannot CHDIR to %1,",CR,LF,"tree past this point not processed" ;badtarg_ptr;an000;bgb
:def 44 " tree past this point not processed" ;badtarg2 ;an000;bgb
:def 45 "%1 bytes disk space freed" ;freebymes1 ;an000;bgb
:def 46 "%1 bytes disk space would be freed" ;freebymes2 ;an000;bgb
:def 47 "Volume %1 created %2 %3",CR,LF ;idmes_arg ;an000;bgb
:def 48 "%1 total allocation units on disk" ;idmes1 ;an000;bgb
:def 49 "%1 bytes in each allocation unit" ;idmes2 ;an000;bgb
;:def 50 "CHKDSK not available on drive %1" ;msgExecFailure ;an000;bgb
:def 51 " Extended Attributes has invalid clusters, attributes truncated" ;Inv_XA_Msg;an000;bgb
:def 52 " Extended Attributes allocation error , attributes truncated" ;Alloc_XA_Msg;an000;bgb
:def 53 "Invalid parameter" ;badsw_arg ;an000;bgb
:use 54 extend15 ;baddrv_arg "invalid drive spec" ;an017;bgb
:use 55 extend3 ;invpath_arg "path not found" ;an017;bgb
:use 56 extend2 ;opnerr_arg "file not found" ;an017;bgb
:def 58 " %1 lost clusters found in %2 chains." ;orph_arg ;an000;bgb
:def 59 CR,LF ;crlf_arg ;an000;bgb
:def 60 " Cannot CHDIR to root",CR,LF ;badcd_arg ;an000;bgb
;an000;bgb
:class D ;an000;bgb
:def 61 " Disk error writing FAT %1" ;badw_arg ;an000;bgb
:def 62 " %1" ;noisy_arg ;an000;bgb
:def 63 "Invalid current directory" ;baddpbdir ;an000;bgb
:def 64 "%1",CR,LF ;file_arg ;an000;bgb
:def 65 " Insufficient room in root directory",CR,LF," Move files from root directory and repeat CHKDSK" ;creatmes;an000;bgb
:def 66 "%1 %2 %3" ;eup_arg ;an000;bgb
:def 67 "%1 %2, %3" ;usp_arg ;an000;bgb
:def 68 "%1%2%3%4%5" ;oth_arg ;an000;bgb
:def 69 "%1%2%3%4" ;time_arg ;an000;bgb
:def 70 "%1 available allocation units on disk" ;idmes2 ;an017;bgb
:use 71 COMMON36 ;Volume Serial Number is %1-%2 ;an024;bgb
:use 72 extend8 ;insufficent memory ;an030;bgb
:use 73 extend26 ;invalid media type ;an033;bgb
:use 74 extend29 ;write fault error ;an033;bgb
:end

View File

@ -0,0 +1,682 @@
TITLE CHKDSK - MS-DOS Disk consistancy checker ;
page ,132 ;
.xlist
include chkseg.inc ;an005;bgb
INCLUDE CHKCHNG.INC
INCLUDE DOSSYM.INC
INCLUDE syscall.inc ;an041;bgb
INCLUDE ioctl.inc ;an041;bgb;an041;bgb
INCLUDE CHKEQU.INC
INCLUDE CHKMACRO.INC
include chkdata.inc ;an005;bgb
include pathmac.inc
CODE SEGMENT PUBLIC PARA 'CODE'
ASSUME CS:DG,DS:NOTHING,ES:DG,SS:dg
EXTRN INT_23:NEAR, readft:near ;an005;bgb
EXTRN FATAL:NEAR, PROMPTYN:NEAR, GET_CURRDIR:NEAR
extrn calc_fatmap_seg:near, FINDCHAIN:NEAR, CHECKERR:NEAR, DIRPROC:NEAR
extrn CHKMAP:NEAR, Main_Init:Near ;an049;bgb
EXTRN CHKCROSS:NEAR, AMDONE:NEAR, UNPACK:NEAR, GET_THISEL2:NEAR
EXTRN PRINTF_CRLF:NEAR, DOCRLF:NEAR, REPORT:NEAR
extrn init_fatmap:near, CHKPRMT_END:near ;an005;bgb
extrn hook_interrupts:near
extrn CHECK_DBCS_CHARACTER:NEAR ;an055;bgb
public SETSTACK, OkDrive, DRVISOK, Root_CD_Ok, NOTVOLID, fat16b, SMALLFAT
public BAD_STACK, RDLOOP, NORETRY1, RDOK, IDOK, ALLDONE, CHECKFILES, GotPath
public IS_ROOT_DIR, NOT_ROOT_DIR, VALID_PATH, ParseName, ScanFile, FRAGCHK
public EACHCLUS, LASTCLUS, NXTCHK, GETNXT, MSGCHK, FILSPOK, CDONE, CDONE1
public PRINTID, FIGREC, Main_Routine, checkit
.list
pathlabl chkdsk1
CHKDSK:
; find out if we have enough memory to do the job
mov cs:save_drive,al ;save drive validity
;;;;int 12h ;1k blocks (640k = 280h) ;an054;bgb;an050;bgb
;;;;mov bx,64 ;number of paragraphs ;an054;bgb;an050;bgb
;;;;mul bx ;640k = a000 ;an054;bgb;an050;bgb
;;;;mov cs:[mem_size],ax ;returns number of 1k blocks ;an054;bgb;an050;bgb
DOS_Call GetCurrentPSP ;Get PSP segment address ;Ac034;bgb
mov cs:psp_segment,bx ;ac034;bgb
mov ds,bx ;ds points to the psp ;Ac034;bgb
Assume DS:Nothing
MOV DX,DS:[2] ;High break
mov cs:[mem_size],dx ;move it into data area ;an054;bgb
MOV BX,0FFFFH ;need at least 64k bytes
MOV CX,CS ;get segment of where we are
SUB DX,CX ;top-of-mem - pgm = # para left in alloc block
CMP DX,0FFFH ; is the space available > 64K ?
; $IF B
JNB $$IF1
MOV CX,4 ; Yes, set SP to BX (FFF0)
SHL DX,CL ; Convert remaining memory to bytes
MOV BX,DX
; $ENDIF
$$IF1:
SETSTACK: ;***Set_Memory*********
CLI
PUSH CS
POP SS
ASSUME SS:DG
MOV SP,BX
STI
PUSH AX
JMP Main_Init ;Go to init routines
;**************************************************************************
; MAIN-ROUTINE
;
; called by - main-init
;
; LOGIC
; *****
; - get the dpb addr
; - set the default drive to here
; - save the directory we are on
; - set the directory to the root of the drive
; - print the volume name
; - get the dpb info
; - get the addr of the fatmap area
; - calculate the amount of stack space we have
;**************************************************************************
Main_Routine:
set_data_segment
OkDrive:
;get the dpb addr from this drive
mov dl,AllDrv ;Get drive number ;AN000;
DOS_Call Get_DPB ;func 32 ;Get DPB pointer ;AC000;
ASSUME DS:NOTHING,cs:DG
CMP AL,-1 ;is this a good drive?
; $IF Z
JNZ $$IF3
;;;;;;;;JNZ DRVISOK ;Bad drive (should always be ok)
LEA DX,BADDRV_arg ;This should never happen ;AC000;
push cs
pop ds
call PRINTf_crlf ; ;AC000;
mov ExitStatus,Bad_Exit ;Get return code ;AC000;
ret ;Go back to Main_Init ;AC000;
; $ENDIF
$$IF3:
MOV WORD PTR CS:[THISDPB+2],DS ;get the dpb segment
set_data_segment ;reset ds to the pgm
MOV WORD PTR [THISDPB],BX ;get the dpb offset
;**Set_Drive_Info*************************************************************
DRVISOK:
push dx
push es
call hook_interrupts
pop es
pop dx
; make this drive the default drive
DEC DL ;A=0 b=1 c=2
DOS_Call Set_Default_Drive ;func 0e - no return ;AC000;
;get the name of the current directory
INC DL ;drive number a=1 b=2 c=3
LEA SI,USERDIR+1 ; ;AC000;
DOS_Call Current_Dir ; ;AC000;
;;;;PUSH CS
;;;;POP ES
;change the current directory to the root
lea DX,rootstr ; ;an005;bgb
DOS_Call ChDir ; ;AC000;
; $IF C ;will this ever happen?
JNC $$IF5
;;;;;;;;jnc Root_CD_Ok ; ;AN000;
MOV DX,OFFSET DG:BADCD_arg
call display_interface ; ;AC000;
mov ExitStatus,Bad_Exit ;Get return code ;AC000;
ret ;Go back to Main_Init ;AC000;
; $ENDIF
$$IF5:
;get the dpb info
LDS BX,[THISDPB] ;ds:bx--> dpb area
ASSUME DS:NOTHING
MOV AX,[BX.dpb_sector_size] ;Bytes/sector
MOV [SSIZE],AX ;Sector size in bytes
MOV AL,[BX.dpb_cluster_mask]
INC AL
MOV [CSIZE],AL ;Sectors per cluster
MOV AX,[BX.dpb_max_cluster] ; number of clusters in the disk
MOV [MCLUS],AX ;Bound for FAT searching
DEC AX ;ax= max clusters - 1 ;an005;bgb
MOV [DSIZE],AX ;Total data clusters on disk ;an005;bgb
CMP AX,4096-8 ;Big or little FAT?
; $IF NB
JB $$IF7
fat16b: INC es:[BIGFAT] ;set 16-bit fat flag to true
MOV es:[EOFVAL],0FFF8H ;set 16-bit compare fields for fat
MOV es:[CHAIN_END],0FFFFh ;Marker for end of chain ;AC000;
MOV es:[BADVAL],0FFF7H ;set 16-bit compare fields for fat
; $ENDIF
$$IF7:
mov ax,[bx.dpb_FAT_size] ;Sectors for one fat (DCR) ;an005;bgb
mov fatsiz,ax ;Sectors for one fat (DCR) ;an005;bgb
MOV CL,[BX.dpb_FAT_count] ;Number of FATs ;an005;bgb
mov fatcnt,cl ;an005;bgb
MOV DX,[BX.dpb_first_FAT] ;First sector of FAT ;an005;bgb
MOV firstfat,dx ;First sector of FAT ;an005;bgb
MOV DX,[BX.dpb_first_sector] ;First sector of data ;ac048;bgb
MOV firstsec,dx ;First sector of data ;ac048;bgb
MOV DX,[BX.dpb_dir_sector] ;First sector of dir ;ac048;bgb
MOV dirsec,dx ;First sector of dir ;ac048;bgb
MOV DX,[BX.dpb_root_entries] ;First sector of dir ;ac048;bgb
MOV root_entries,dx ;First sector of dir ;ac048;bgb
set_data_segment ;reset ds to point to data area
;calc fatmap area
SMALLFAT: ;do this for both size fats
;old calculation
;;;;DEC AX ;ax= max clusters - 1 ;an005;bgb
;;;;MOV [DSIZE],AX ;Total data clusters on disk ;an005;bgb
;;;;MOV AX,[BX.dpb_FAT_size] ;Sectors for one fat (DCR) ;an005;bgb
;;;;MOV CX,AX ;CX = Sectors/Fat ;an005;bgb
;;;;MUL [SSIZE] ;times bytes/sector = bytes per fat ;an005;bgb
;;;;ADD fatmap,AX ;Allocate FAT space ;an005;bgb
;;;;MOV AX,fatmap ; get seg of fatmap ;an005;bgb
Root_CD_Ok: ; ;AN000;
;set dta area----do i need to do this since we are using int 25?
;set it to fat table
call calc_fatmap_seg ;find the addr of where to put the fat map ;an005;bgb
;see if we still have enough memory
mov ax,mem_size ;get top of memory
cmp ax,end_of_fatmap ;mem_size must be greater or equal
; $IF B ; if not, display error msg
JNB $$IF9
MOV DX,OFFSET DG:no_mem_arg
invoke printf_crlf
jmp alldone ;finished with pgm
; $ENDIF
$$IF9:
push ds ;save ds
mov ds,fattbl_seg ;get seg
xor dx,dx ;ds:dx--> dta area
;;;;mov fatmap,dx
DOS_Call Set_DMA ;function 1a ;AC000;
pop ds ;restore ds
;look for volume entry in dir
lea DX,volid ;Look for VOL ID ;an005;bgb
DOS_Call Dir_Search_First ;function 11 ;AC000;
CMP AL,0 ;did we find it?
; $IF Z ;yes
JNZ $$IF11
;;;;;;;;JZ NOTVOLID
CALL PRINTID ;print volume name, date, time
; $ENDIF
$$IF11:
NOTVOLID:
call get_serial_num ;print volume serial number ;an024;bgb
;;;;call hook_interrupts
; calculate the place where we run out of ram space ;an005;bgb
;;;;ADD AX,[MCLUS] ;5000 ;fatmap seg + num of clusters? ;an005;bgb
;;;;ADD AX,2 ;5002 ;Insurance ;an005;bgb
;;;;MOV [SECBUF],AX ;Allocate fatmap space ;an005;bgb
mov ax, offset dg:chkprmt_end ;this label must be the last thing in the code segment
mov [secbuf],AX ;location of read/write buffer for dir entries ;an005;bgb
;;;;ADD AX,[SSIZE] ;5202 ;an005;bgb
;;;;ADD AX,20 ;5216 ;Insurance ;an005;bgb
mov ax,0ffffh ;get end of segment
lea bx,fattbl ;get end of program
sub ax,bx ;this is the amount of stack space we have
MOV [STACKLIM],AX ;Limit on recursion ;an005;bgb
; see if we have already overrun the stack
MOV DI,SP ;where is the stack pointer now? ;an005;bgb
SUB DI,100H ; Want AT LEAST this much stack from ;an005;bgb
; our current location ;an005;bgb
CMP DI,AX
; $IF B
JNB $$IF13
;;;;;;;;JB BAD_STACK ; Already in trouble
BAD_STACK:
MOV BX,OFFSET DG:STACKMES ;Out of stack
PUSH CS
POP DS
JMP FATAL
; $ENDIF
$$IF13:
;
;**Read in FAT*****************************************************************
;;;;MOV DI,fatsiz ;sectors per fat ;an005;bgb
;;;;MOV CL,[BX.dpb_FAT_count] ;Number of FATs
;;;;MOV DX,[BX.dpb_first_FAT] ;First sector of FAT
mov cx,fatsiz ;number of sectors to read ;an005;bgb
mov dx,firstfat ;starting sector number ;an005;bgb
mov es,fattbl_seg ;set up bx for read-disk ;an005;bgb
xor bx,bx ;an005;bgb
MOV AL,[ALLDRV] ;set up al with drive letter for read-disk
DEC AL ;zero based
;;;;MOV AH,1
RDLOOP:
;;;;XCHG CX,DI ;DI has # of Fats
call readft ; readft (); ;AN005;bgb
; $IF C ; could the fat be read from disk? ;AN005;bgb
JNC $$IF15
inc byte ptr [nul_arg] ;an005;bgb
;;;;;;;;mov [fatal_arg2],offset dg:baddrvm ;an005;bgb
mov [fatmsg2],offset dg:baddrvm ;an005;bgb
lea BX,badread ;an022;bgb
JMP FATAL ;Couldn't read any FAT, BARF ;an005;bgb
; $ENDIF ;fat could be read from disk ;AN005;bgb
$$IF15:
; savereg <dx,cx,di,ax> ;an005;bgb
; mov Read_Write_Relative.Start_Sector_High,0 ; ;AN000;
; call Read_Disk ;Read in the FAT ;AC000;
; $IF C
;;;;;;;;JNC RDOK
;;;;;;;;mov [badrw_str],offset dg:reading
; POP AX ; Get fat# in ah
; PUSH AX ; Back on stack
; xchg al,ah ; Fat # to AL
; xor ah,ah ; Make it a word
; mov [badrw_num],ax
; mov dx,offset dg:badr_arg
; invoke printf_crlf
; restorereg <ax,cx,di,dx> ;an005;bgb
; INC AH
; ADD DX,DI
; LOOP RDLOOP ;Try next FAT
;;;;;;;;JMP NORETRY1 ;Couldn't read either ;AC000;
NORETRY1:
; inc byte ptr [nul_arg]
; mov [fatal_arg2],offset dg:baddrvm
; MOV BX,OFFSET DG:BADRDMES
; JMP FATAL ;Couldn't read any FAT, BARF
; $ENDIF
RDOK: ;**Check_for_FAT_ID**********************************************
;;;;restorereg <ax,ax,ax,ax> ;Clean up ;an005;bgb
mov es,fattbl_seg ;segment of fat-table ;an005;bgb
xor si,si ;offset of first byte in fat-table ;an005;bgb
;;;;LODSB ;Check FAT ID byte
mov al,byte ptr es:[si] ;get first byte of fat table
CMP AL,0F8H ;is it the correct id byte?
; $IF B,AND
JNB $$IF17
;;;;;;;;JAE IDOK
CMP AL,0F0H ;if not, Is it a "strange" medium?
; $IF NZ
JZ $$IF17
;;;;;;;;jz IDOK ;neither fat nor strange
MOV DX,OFFSET DG:BADIDBYT ;FAT ID bad
CALL PROMPTYN ;Ask user to stop or not
; $IF NZ
JZ $$IF18
;;;;;;;;;;;;JZ IDOK
JMP ALLDONE ;User said stop
; $ENDIF
$$IF18:
; $ENDIF
$$IF17:
;initialize the fatmap area to all zeros
IDOK:
call init_fatmap
;set the dta addr to here for all searches
MOV DX,OFFSET DG:DIRBUF ;FOR ALL SEARCHING
DOS_Call Set_DMA ; ;AC000;
XOR AX,AX ;zero out ax
PUSH AX ;I am root
PUSH AX ;Parent is root
;
set_data_segment
checkit:
CALL DIRPROC
CALL CHKMAP ;Look for badsectors, orphans
CALL CHKCROSS ;Check for second pass
INVOKE DOCRLF ;display new line
CALL REPORT ;finished, display data to screen
;*****************************************************************************
ALLDONE:
CALL AMDONE
;;;;;MOV AH,EXIT
;;;;;;;;XOR AL,AL
;;;;;; ;mov ExitStatus,Bad_Exit ;Get return code ;AC000;
;;;;;;;;INT 21H
ret ;Ret to Main_Init for common exit ;AN000;
ASSUME DS:DG
;**Extent_Check***************************************************************
Break <Check for extents in specified files>
;
; Search the directory for the files specified on the command line and report
; the number of fragmented allocation units found in each one. We examine the
; given path name for a directory. If it is found, we CHDIR to it. In any
; event, we move to the file name part and do a parseFCB call to convert it
; into an FCB for a dir_search_first. If the parse did NOT advance the
; pointer to the null byte terminating the string, then we have a bogus anme
; and we should report it.
;
CHECKFILES:
set_data_segment
; see if there is a '\' in the path name
MOV DI,OFFSET DG:PATH_NAME
MOV SI,DI
MOV CX, FNAME_LEN ; ;an011;bgb
ADD DI,CX ; ES:DI points to char AFTER last char
DEC DI ; Point to last char
doagain: MOV AL,[DIRCHAR] ;try to find '\' in path name
STD
REPNE SCASB
CLD
; $IF Z ;a '\' was found in path ;an055;bgb
JNZ $$IF21
mov al,[di] ;get byte preceding '\' ;an055;bgb
call check_dbcs_character ;see if dbcs leading char ;an055;bgb
; $IF C ;carry means dbcs leading char ;an055;bgb
JNC $$IF22
jmp doagain ;so ignore ;an055;bgb
; $ELSE ;an055;bgb
JMP SHORT $$EN22
$$IF22:
jmp GotPath ;found a '\' and not dbcs ;an055;bgb
; $ENDIF ;an055;bgb
$$EN22:
; $ENDIF ;an055;bgb
$$IF21:
;;;;;;;;;;;;;;;;;;;;;JZ GotPath ; found path char. ;an055;bgb
; No '\' was found. set up pointers for parse FCB call.
MOV DI,OFFSET DG:PATH_NAME
CMP BYTE PTR [DI+1],':' ;was a drive letter entered?
JNZ ParseName
ADD DI,2
JMP SHORT ParseName
;*****************************************************************************
; found a '\' in the path name
;Change directories and set up the appropriate FCB
GotPath:
INC DI ; DI points AT the path sep
PUSH WORD PTR [DI] ; Save two chars here
PUSH DI ; Save location
SUB SI,DI
JZ IS_ROOT_DIR ; SI=DI=First char which is a dirchar
NEG SI
CMP SI,2
JNZ NOT_ROOT_DIR
CMP BYTE PTR [DI-1],':' ; d:\ root spec?
JNZ NOT_ROOT_DIR ; Nope
IS_ROOT_DIR:
INC DI ; Don't zap the path sep, zap NEXT char
NOT_ROOT_DIR:
MOV BYTE PTR [DI],0
MOV DX,OFFSET DG:PATH_NAME
DOS_Call Chdir ; ;AC000;
POP DI ; Recall loc
POP WORD PTR [DI] ; recall chars
JNC VALID_PATH
INVOKE DOCRLF
MOV DX,OFFSET DG:INVPATH_arg
invoke printf_crlf
JMP CDONE1
;*****************************************************************************
VALID_PATH:
INC [DIR_FIX]
INC DI ; Point past path sep to first char of name
ParseName:
; parse the filename and get back a formatted fcb for it in es:di
MOV SI,DI ; DS:SI points to name
MOV DI,offset dg:FCB_copy ; ES:DI points to FCB
MOV AL,ALLDRV ; drive number
STOSB ; put it into fcb
DEC DI ; Back to start of FCB
MOV pFileName,SI ; save end of file name
MOV AL,00000010B ; tell parse to change drive letter if needed
DOS_Call Parse_File_Descriptor ; ;AC000;
CMP BYTE PTR [SI],0 ;ds:si should point past filename
JZ ScanFile
;
; Twiddle the file name to be truly bogus. Zorch the drive letter
;
MOV BYTE PTR es:[DI],-1
ScanFile:
INVOKE DOCRLF
;set dma pointer to here
MOV DX,OFFSET DG:DIRBUF ;FOR ALL SEARCHING
MOV BP,DX
ADD BP,27 ;bp points to clus in the dir entry
DOS_Call Set_DMA ;set dma ptr here for dir search ;AC000;
;try to find the file specified
MOV AH,DIR_SEARCH_FIRST ;Look for the first file
FRAGCHK:
MOV DX,offset dg:FCB_copy
INT 21H
OR AL,AL ;Did we find it?
JNZ MSGCHK ;No -- we're done
; we found the file
; look for fragmentation
XOR AX,AX ;Initialize the fragment counter
MOV SI,[BP] ;Get the first cluster ;an005;bgb
CALL UNPACK ;see what that cluster points to
CMP DI,[EOFVAL] ;End-of-file?
JAE NXTCHK ;Yes -- go report the results
INC SI
CMP SI,DI
JZ EACHCLUS
INC AX
EACHCLUS:
MOV [OLDCLUS],DI ;Save the last cluster found
MOV SI,DI ;Get the next cluster
CALL UNPACK
INC [OLDCLUS] ;Bump the old cluster
CMP DI,[OLDCLUS] ;Are they the same?
JNZ LASTCLUS ;No -- check for end-of-file
JMP SHORT EACHCLUS ;Continue processing
LASTCLUS:
CMP DI,[EOFVAL] ;End-of-file?
JAE NXTCHK ;Yes -- go report the results
INC AX ;No -- found a fragement
JMP SHORT EACHCLUS ;Continue processing
NXTCHK: ;reached the end of a file
OR AX,AX ;did we find any fragmentation?
JZ GETNXT
;we found fragmentation
MOV [FRAGMENT],2 ;Signal that we output at least one file
inc ax ;bump by one for ends
mov [block_num],ax
mov word ptr rarg1,ax ; ;an011;bgb
mov word ptr rarg1+2,0
mov si,offset dg:dirbuf ;point to filename ;an011;bgb
INC SI ;move pointer past drive letter
; get the full path name for this file
CALL get_THISEL2
; print it out
mov dx,offset dg:extent_arg
invoke printf_crlf
GETNXT:
MOV AH,DIR_SEARCH_NEXT ;Look for the next file
JMP FRAGCHK
MSGCHK:
CMP AH,DIR_SEARCH_FIRST ;was this the first file searched for?
JNZ FILSPOK
; MOV SI,offset dg:FCB_copy + 1 ;File not found error
; CALL get_THISEL2
MOV SI,pFileName
CALL get_currdir
mov dx,offset dg:OPNERR_arg
invoke printf_crlf ;bad file spec
jmp short cdone
FILSPOK:
CMP BYTE PTR [FRAGMENT],2
JZ CDONE
; all files were ok
mov dx,offset dg:NOEXT_arg
invoke printf_crlf
CDONE:
CMP BYTE PTR [DIR_FIX],0
JZ CDONE1
MOV DX,OFFSET DG:USERDIR
DOS_Call ChDir ; ;AC000;
CDONE1:
RET
; This is the old parameter passing scheme ;ac048;bgb
; inputs: AH - the sector number within the cluster ;ac048;bgb
; BX - cluster number ;ac048;bgb
; output: DX - absolute sector number ;ac048;bgb
;***************************************************************************** ;ac048;bgb
; FIGREC - This procedure calculates the absolute sector number of a logical ;ac048;bgb
; drive, given any cluster number and the sector within that cluster. ;ac048;bgb
; You can use this to find the sector number for a file. ;ac048;bgb
; ;ac048;bgb
; This procedure was entirely re-written for dos 4.0, since the ;ac048;bgb
; sector number can now be a DOUBLE word value. ;ac048;bgb
; ;ac048;bgb
; called by: getent in chkproc ;ac048;bgb
; ;ac048;bgb
; inputs: BX - cluster number ;ac048;bgb
; AH - sector number within cluster ;ac048;bgb
; csize - sectors per cluster (from dpb) ;ac048;bgb
; firstsec - starting sector number of the data area (from dpb) ;ac048;bgb
; ;ac048;bgb
;outputs: DX - absolute sector number (low order) ;ac048;bgb
; INT26.start_sector_high (hi order) ;ac048;bgb
; ;ac048;bgb
;regs changed: DX only ;ac048;bgb
; ;ac048;bgb
;formula: cluster (3-fff7) * secs/cluster (1-8) = (3-7ffb8) ;ac048;bgb
; + sector-offset (0-8) + first-sector (1-ffff) = (7ffb9-8ffbf) ;ac048;bgb
; ;ac048;bgb
; logic: 1. adjust the cluster number, since the 1st two clusters in the fat ;ac048;bgb
; are not used. cluster number can be from 3-fff7. ;ac048;bgb
; 2. get the sectors-per-cluster, and multiply it times cluster number ;ac048;bgb
; in AX. since this is a word multiply, the high order number goes ;ac048;bgb
; into DX. ;ac048;bgb
; 3. add in the sector-number-within-the-cluster. Each cluster ;ac048;bgb
; (usually) contains several sectors within a cluster. This sector ;ac048;bgb
; number is that number. It may be from zero to the max number of ;ac048;bgb
; sectors/cluster (which can be up to 8 so far on IBM systems). ;ac048;bgb
; Do an ADC in case there is a overflow of the word register. ;ac048;bgb
; 4. add in the starting cluster number of the data area. This now ;ac048;bgb
; gives you the logical sector number within that drive. ;ac048;bgb
;***************************************************************************** ;ac048;bgb
procedure figrec,NEAR ;ac048;bgb
push ax ;save registers ;ac048;bgb
push bx ;save registers ;ac048;bgb
push cx ;save registers ;ac048;bgb
;ac048;bgb
xor ch,ch ;clear out hi byte of sector-offset ;ac048;bgb
mov cl,ah ;move sector-offset into cx ;ac048;bgb
mov ax,bx ;move cluster number into ax for mult ;ac048;bgb
;ac048;bgb
xor bh,bh ;zero out bh ;ac048;bgb
mov bl,csize ;get sectors per cluster ;ac048;bgb
dec ax ; sub 2 for the 1st 2 unused clus in the fat ;ac048;bgb
dec ax ; ;ac048;bgb
mul bx ;ax=low word, dx=hi word ;ac048;bgb
;ac048;bgb
add ax,cx ;add sector offset ;ac048;bgb
adc dx,0 ;inc hi word if overflow ;ac048;bgb
add ax,[firstsec] ;add first data sector ;ac048;bgb
adc dx,0 ;inc hi word if overflow ;ac048;bgb
;ac048;bgb
mov Read_Write_Relative.Start_Sector_High,dx ;save hi value ;ac048;bgb
mov dx,ax ;convert to old format- dx=low ;ac048;bgb
;ac048;bgb
pop cx ;ac048;bgb
pop bx ;ac048;bgb
pop ax ;ac048;bgb
RET ;ac048;bgb
endproc figrec ;ac048;bgb
;*****************************************************************************
SUBTTL PRINTID - Print Volume ID info
PAGE
PRINTID:
ASSUME DS:DG
call docrlf ; ;AN000;
;get volume name ;an012;bgb
xor si,si ;Point at DTA where find first just done;;an005;bgb
lea DI,arg_buf ;Where to put vol name for message ;AC000;
add si,DirNam ;Point at the vol label name ;AN000;
;;;;;;;;lea DI,arg_buf ;Point at vol label location in arg_Buf ;AC000;
MOV CX,11 ; Pack the name
push ds ;an005;bgb
mov ds,fattbl_seg ;an005;bgb
REP MOVSB ; Move all of it
;get the year ;an012;bgb
xor si,si ;Get back pointer to FCB ;an009;bgb
mov ax,ds:[si].DirDat ;yyyyyyym mmmddddd Put in SysDisp form ;AN009;bgb
and ax,Year_Mask ;yyyyyyy0 00000000 ;AN000;
shr ax,1 ;0yyyyyyy 00000000 ;AN000;
xchg al,ah ;00000000 0yyyyyyy ;AN000;
add ax,1980 ; ;AN000;
mov es:Sublist_msg_Idmes.Sublist_Offset+(size Sublist_Struc),ax ; ;AN009;bgb
;get the month ;an012;bgb
mov ax,ds:[si].DirDat ;yyyyyyym mmmddddd ;AN009;bgb
and ax,Month_Mask ;0000000m mmm00000 ;AN000;
mov cl,5 ; ;AN000;
shr ax,cl ;00000000 0000mmmm ;AN000;
mov cl,al ;0000mmmm ;AN000;
;get the day ;an012;bgb
mov ax,ds:[si].DirDat ;yyyyyyym mmmddddd ;AN009;bgb
and ax,Day_Mask ;00000000 000ddddd ;AN000;
mov ah,cl ;0000mmmm 000ddddd ;AN000;
xchg ah,al ;make it display correctly ;an012;bgb
mov es:Sublist_msg_Idmes.Sublist_Segment+(size Sublist_Struc),ax ; ;AN009;bgb
;get the time ;an012;bgb
mov ax,ds:[si].DirTim ;hhhhhmmm mmmsssss ;AN009;bgb
and ax,Hour_Mask ;hhhhh000 00000000 ;AN000;
mov cl,11 ; ;AN000;
shr ax,cl ;00000000 000hhhhh ;AN000;
mov ch,al ;000hhhhh ;AN000;
mov ax,ds:[si].DirTim ;hhhhhmmm mmmsssss ;AN009;bgb
and ax,Minute_Mask ;00000mmm mmm00000 ;AN000;
mov cl,3 ; ;AN000;
shl ax,cl ;00mmmmmm 00000000 ;AN000;
mov al,ch ;00mmmmmm 000hhhhh ;AN000;
mov es:Sublist_msg_Idmes.Sublist_Offset+(size Sublist_Struc)+(size Sublist_Struc),ax ;AN009;bgb
mov es:Sublist_msg_Idmes.Sublist_Segment+(size Sublist_Struc)+(size Sublist_Struc),0 ;AN009;bgb
pop ds ;an009;bgb
Message Idmes_Arg ; the parts out as needed ;AC000'
;;;;;;;;call doCRLF
ret ;
;***************************************************************************** ;an024;bgb
; Get the volume serial number ;an024;bgb
;***************************************************************************** ;an024;bgb
; Input: FCB_Drive ;an024;bgb
; Output: SerNum if no carry ;an024;bgb
; Notes: Only DOS Version 3.4 and above will contain serial numbers ;an024;bgb
;***************************************************************************** ;an024;bgb
PUBLIC GET_SERIAL_NUM ;an024;bgb
procedure Get_Serial_Num,NEAR ;AN000;S ;an024;bgb
mov al,GENERIC_IOCTL ;AN000;S ;an041;bgb;an024;bgb
xor bx,bx ;zero out bx ;an041;bgb;an024;bgb
mov bl,alldrv ;AN000;S Which drive to check ;an024;bgb
mov ch,rawio ;8 = disk io ;an041;bgb;an024;bgb
mov cl,Get_Media_Id ;66h = get media id ;an041;bgb;an024;bgb
LEA dx,SerNumBuf ;AN000;S Pt to the buffer ;an024;bgb
Dos_call ioctl ;AN000;S Make the call ;an041;bgb;an024;bgb
; $IF NC
JC $$IF26
message msgserialnumber ;an024;bgb
; $ENDIF
$$IF26:
ret ;AN000;S ;an024;bgb
endproc Get_Serial_Num ;AN000;S ;an024;bgb
pathlabl chkdsk1 ;an024;bgb
CODE ENDS
END CHKDSK


View File

@ -0,0 +1,449 @@
TITLE CHKDSK - MS-DOS Disk consistancy checker
page ,132 ;
.xlist
include chkseg.inc
INCLUDE CHKCHNG.INC
INCLUDE DOSSYM.INC
INCLUDE CHKEQU.INC
INCLUDE CHKMACRO.INC
include pathmac.inc
.list
SUBTTL Initialized Data
PAGE
CONST SEGMENT PUBLIC PARA 'DATA'
EXTRN BADVER:byte,BADDRV_ARG:word,INVPATH_ARG:word
EXTRN FILE_ARG:word
EXTRN BADCD_ARG:word,BADSUBDIR:byte
EXTRN BADDRVM:byte
EXTRN BADIDBYT:byte
EXTRN OPNERR_ARG:word,NOEXT_ARG:word,EXTENT_ARG:word
EXTRN IDMES_ARG:WORD
EXTRN FILE_ARG1:WORD,FILE_ARG2:WORD
EXTRN badrw_num:word,BADRW_STR:WORD,BLOCK_NUM:WORD
EXTRN BADSW_ARG:WORD,DSKSPC:WORD
EXTRN HIDMES:WORD,DIRMES:WORD,FILEMES:WORD,ORPHMES2:WORD
EXTRN ORPHMES3:WORD,BADSPC:WORD,FRESPC:WORD
EXTRN TOTMEM:WORD,FREMEM:WORD,REPORT_ARG:WORD,CRLF_ARG:WORD
EXTRN RARG1:dWORD,RARG3:dWORD,ORPHCNT:dWORD ;an049;bgb
EXTRN SubstErr:BYTE
extrn tot_bytes_lo:word, tot_bytes_hi:word
extrn SWITCHAR:byte,TCHAR:byte,HECODE:byte,CONBUF:byte
extrn DOTMES:byte,NOISY:byte,HAVFIX:byte
extrn DOFIX:byte,DIRBUF:near,PARSTR:byte
extrn NUL:byte,ERRSUB:word,ALLFILE:byte
extrn ORPHFCB:byte,ORPHEXT:byte,HIDCNT:dword
extrn HIDSIZ:word,FILCNT:dword,FILSIZ:word,DIRCNT:dword ;an049;bgb
extrn DIRSIZ:word,CROSSCNT:dword,BADSIZ:word ;an049;bgb
extrn ORPHSIZ:word ;an049;bgb
extrn LCLUS:word ;an049;bgb
extrn USERDIR:byte,FRAGMENT:byte
extrn ALLDRV:byte,FIXMFLG:byte,DIRCHAR:byte
extrn EOFVAL:word ;an050;bgb
extrn Idmes2:Byte,Idmes1:Byte,idmes3:byte ;an017;bgb
CONST ENDS
SUBTTL Un-initialized Data
PAGE
DATA SEGMENT PUBLIC PARA 'DATA'
extrn THISDPB:dword,DOTSNOGOOD:byte,NUL_ARG:byte
extrn NAMBUF:byte,SRFCBPT:word
extrn ISCROSS:byte,MCLUS:word,CSIZE:byte,SSIZE:word
extrn DSIZE:word,ARG1:word,ARG_BUF:byte,ERRCNT:byte
extrn USERDEV:byte,HARDCH:dword,CONTCH:dword
extrn mem_size:word ;an055;bgb
extrn psp_segment:word ;an030;bgb
extrn write_fault:byte ;an045;bgb
DATA ENDS
CODE SEGMENT PUBLIC PARA 'CODE'
ASSUME CS:DG,DS:DG,ES:DG,SS:DG
EXTRN INT_23:NEAR
EXTRN PROMPTYN:NEAR,GET_CURRDIRERR:NEAR,GET_CURRDIR:NEAR
EXTRN FINDCHAIN:NEAR,CHECKERR:NEAR
EXTRN Write_Disk:Near, multiply_32_bits:near
PUBLIC PRINTF_CRLF,DOCRLF,SUBERRP,FCB_TO_ASCZ,EPRINT
PUBLIC DOINT26,DOTCOMBMES,REPORT
public ramcarv
;EPRINT:
; CALL CHECKERR
; JNZ RET14
; cmp byte ptr [nul_arg],0
; jnz hav_eprint_arg
; mov [file_arg2],offset dg:nul
;hav_eprint_arg:
; mov [file_arg1],dx
; ;mov dx,offset dg:file_arg
; mov dx,file_arg ;Get offset of message ;AC000;
; call printf_crlf
; mov byte ptr [nul_arg],0
;RET14: ret
EPrint:
call CheckErr ;See if we should display msg
pathlabl chkdsk2
; $IF Z ;Yes if Z set ;AC000;
JNZ $$IF1
push dx ;Save message ;AC000;
Message File_Arg ;Put out file in question ;AC000;
pop dx ;Get back message ;AC000;
call Printf_CRLF ;Print it
cmp byte ptr [nul_arg],0 ;Is there a second message?
; $IF NZ ;Yes if not nul ;AC000;
JZ $$IF2
mov dx,File_Arg2 ;Display it ;AN000;
call Printf_CRLF ; ;AN000;
; $ENDIF ; ;AC000;
$$IF2:
mov byte ptr [nul_arg],0 ;Re-init this field
; $ENDIF
$$IF1:
ret ;
DOTCOMBMES:
CMP [NOISY],0
JZ SUBERRP
mov [file_arg2],dx
CALL get_currdirERR
;MOV DX,OFFSET DG:CENTRY ;Centry got split into 3 msg's
;inc byte ptr [nul_arg] ;
CALL EPRINT
RET
SUBERRP:
MOV AL,1 ;found a subdir error
XCHG AL,BYTE PTR [ERRSUB] ;set error flag and get old flag
CMP AL,0 ;were any errors found before?
; $if z ;no errors found yet
JNZ $$IF5
;JNZ RET32
MOV SI,OFFSET DG:NUL ;display error msgs
CALL get_currdirERR
MOV DX,OFFSET DG:BADSUBdir
CALL EPRINT
; $endif
$$IF5:
RET32: RET
;****************************************************************************
; called by: get_thisel2
; inputs: DS:SI - pointer to file name
;****************************************************************************
FCB_TO_ASCZ: ;Convert DS:SI to ASCIZ ES:DI
PUSH CX
;move filename from ds:si to es:di
MOV CX,8 ; Pack the name
REP MOVSB ; Move all of it
main_kill_tail:
; delete trailing spaces in name
CMP BYTE PTR ES:[DI-1]," " ;was the last char in name a space?
JNZ find_check_dot
DEC DI ; Back up over trailing space
INC CX
CMP CX,8
JB main_kill_tail
find_check_dot:
; ???
CMP WORD PTR [SI],(" " SHL 8) OR " "
JNZ got_ext ; Some chars in extension
CMP BYTE PTR [SI+2]," "
JZ find_done ; No extension
got_ext:
; move period for extension
MOV AL,"."
STOSB
; move 3 byte extension
MOV CX,3
REP MOVSB
ext_kill_tail:
;delete trailing blanks
CMP BYTE PTR ES:[DI-1]," " ;
JNZ find_done ;
DEC DI ; Back up over trailing space
JMP ext_kill_tail ;
find_done: ;
; put hex zero at the end
XOR AL,AL ;
STOSB ; NUL terminate
POP CX
RET
DOINT26:
; PUSH CX ;reg saves are handled in write_disk ;ac048;bgb;an045;bgb
; PUSH DX ;reg saves are handled in write_disk ;ac048;bgb;an045;bgb
; PUSH BX ;reg saves are handled in write_disk ;ac048;bgb;an045;bgb
call Write_Disk ; ;an045;bgb;AC000;
; POP BX ;reg saves are handled in write_disk ;ac048;bgb;an045;bgb
; POP DX ;reg saves are handled in write_disk ;ac048;bgb;an045;bgb
; POP CX ;reg saves are handled in write_disk ;ac048;bgb;an045;bgb
; JNC RET23 ;ac048;bgb;an045;bgb
;MOV SI,OFFSET DG:WRITING ;ac048;bgb;an045;bgb
;CALL DSKERR ;ac048;bgb;an045;bgb
; $IF C ;ac048;bgb;an045;bgb
JNC $$IF7
mov dx,offset dg:write_fault ;ac048;bgb;an045;bgb
invoke printf_crlf ;ac048;bgb;an045;bgb
; $ENDIF ;ac048;bgb;an045;bgb
$$IF7:
; ;ac048;bgb;ac048;bgb;an045;bgb
;Need to handle 'Fail' option of critical error here. ;ac048;bgb;an045;bgb
; ;ac048;bgb;an045;bgb
;ac048;bgb;an045;bgb
; JZ DOINT26 ;ac048;bgb;an045;bgb
RET23: RET ;ac048;bgb;an045;bgb
;**************************************
; Prints all reporting data
;**************************************
REPORT:
;total disk space
mov bx,offset dg:dskspc
mov dx,tot_bytes_hi ;total bytes in disk ;AN006;bgb
mov ax,tot_bytes_lo ;total bytes in disk ;AN006;bgb
xor si,si ;no file count
xor di,di ;no file count
call Report_Mes_2 ; ;AN006;bgb
;hidden files
mov ax,hidsiz ;get cluster count ;an049;bgb
or ax,ax ;are there any hidden files?
; $IF NZ ;yes ;AC000;
JZ $$IF9
mov si,word ptr hidcnt ;si=low file count ;an049;bgb
mov di,word ptr hidcnt+2 ;di=hi file count ;an049;bgb
mov bx,offset dg:hidmes ;bx=msg ;
call report_mes_1 ;
; $ENDIF ; ;AC000;
$$IF9:
;space in subdirectories
mov ax,dirsiz ;get cluster count
or ax,ax ;Are there any directories? ;an049;bgb
; $IF NZ ;yes ;AC000;
JZ $$IF11
mov si,word ptr dircnt ;si=low file count ;an049;bgb
mov di,word ptr dircnt+2 ;di=hi file count ;an049;bgb
mov bx,offset dg:dirmes ;bx=msg
call report_mes_1 ;an049;bgb
; $ENDIF ; ;AC000;
$$IF11:
;user files
mov ax,filsiz ;get cluster count
or ax,ax ;Are there any user files? ;an049;bgb
; $IF NZ ;yes ;AC000;
JZ $$IF13
mov si,word ptr filcnt ;si=lo file count ;an049;bgb
mov di,word ptr filcnt+2 ;di=hi file count ;an049;bgb
mov bx,offset dg:filemes ;bx=msg
call report_mes_1
; $ENDIF ; ;AC000;
$$IF13:
;chains of lost clusters
mov ax,orphsiz ;get cluster count
or ax,ax ;Are there any lost clusters? ;an049;bgb
; $IF NZ ;yes ;AC000;
JZ $$IF15
mov si,word ptr orphcnt ;si=lo file count
mov di,word ptr orphcnt+2 ;di=hi file count
cmp dofix,0 ;/F entered?
; $IF Z ;no ;AC000;
JNZ $$IF16
mov bx,offset dg:orphmes3 ;bytes would be recovered
; $else
JMP SHORT $$EN16
$$IF16:
mov bx,offset dg:orphmes2 ;bytes were recovered
; $ENDIF ; ;AC000;
$$EN16:
call report_mes_1
; $ENDIF ; ;AC000;
$$IF15:
;clusters of bad spots
mov ax,badsiz ;get cluster count
or ax,ax ;Are there any bad spots on disk?
; $IF NZ ;if low word > zero, then yes ;AC000;
JZ $$IF20
xor si,si ;no files to count
xor di,di ;no files to count
mov bx,offset dg:badspc ;Issue report
call report_mes_1
; $ENDIF ; ;AC000;
$$IF20:
;bytes on disk left - free space
mov ax,[dsize] ;get total disk clusters
sub ax,[dirsiz] ; - dirs
sub ax,[filsiz] ; - files
sub ax,[hidsiz] ; - hidden files
sub ax,[badsiz] ; - bad spots
sub ax,[orphsiz] ; - lost clusters recovered
sub ax,[lclus] ; - lost clusters not recovered
xor si,si
xor di,di
mov bx,offset dg:frespc
call report_mes_1 ;Free space is whats left
call docrlf ; ;AN000;
;size of each allocation unit
xor dx,dx ;Figure out cluster size ;AN000;
xor ah,ah ; ;AN000;
mov cx,SSize ;Bytes/sector * ;AN000;
mov al,CSize ; Sectors/cluster ;AN000;
mul cx ; = Bytes/Cluster in AX ;AN000;
mov bx,offset dg:idmes2 ;Allocation size message ;AN000;
xor si,si
xor di,di
call Report_Mes_2 ; ;AN000;
;total clusters
mov ax,Mclus ;Allocation units available ;AN000;
dec ax ;MCLUS is # clusters+1
xor dx,dx ; ;AN000;
mov bx,offset dg:idmes1 ; ;AN000;
xor si,si
xor di,di
call Report_Mes_2 ; ;AN000;
;;;;;;;;call docrlf ; ;an017;bgb
;avail clusters ;an017;bgb
public avail_clus
avail_clus:
mov ax,[dsize] ;total clusters on disk ;an017;bgb
sub ax,[dirsiz] ; - clusters in subdirs ;an017;bgb
sub ax,[filsiz] ; - user files ;an017;bgb
sub ax,[hidsiz] ; - hidden files ;an017;bgb
sub ax,[badsiz] ; - bad spots ;an017;bgb
sub ax,[orphsiz] ; - lost clusters recovered ;an017;bgb
sub ax,[lclus] ; - lost clusters not recovered ;an017;bgb
mov bx,offset dg:idmes3 ; ;an017;bgb
xor dx,dx ; ;AN017;bgb
xor si,si
xor di,di
call Report_Mes_2 ;dont convert to bytes! ;an017;bgb
call docrlf ;an017;bgb
;dcl Jan 8, 87 Compensate for RAM Carving - Start
ramcarv:
push es ;AN000;
xor bx,bx ;AN000;
mov ah,0c1h ; return Ext'd Bios Data Seg Address ;AN000;
int 15h ;AN000;
; $IF NC ; ram carving exists if no carry ;AC000; ;AN000;
JC $$IF22
xor ax,ax ; zero out ax
mov al,byte ptr es:[0] ; pointer to # of 1k blocks of RAM Carve;AN000;
mov dx,64 ; convert 1k blocks to paras ;AN000;
mul dx ;AN000;
mov bx,ax ; save value in BX ;AN000;
; $ENDIF ; ;AC000; ;AN000;
$$IF22:
pop es ;AN000;
;dcl Jan 8, 87 Compensate for RAM Carving - End
mov ax,[mem_size] ;Find out about memory
add ax,bx ; dcl Jan 8, 87 Compensate for RAM Carving
mov dx,16 ;Mul to convert kbytes to bytes
mul dx
mov bx,offset dg:totmem
call report_mes_2
mov ax,[mem_size]
;;;;;;; mov dx,psp_segment ;an030;bgb
sub ax,psp_segment ;an030;bgb
mov dx,16
mul dx
mov bx,offset dg:fremem
call report_mes_2
ret
;*************************************************************
;
; Print the message specified by the control string.
;
; REPORT_MES_1
; On entry:
; BX contains the address of the control string.
; AX contains a cluster count for the %ld argument in the control string.
; CX contains a word count for the %d argument in the control string
; or is meaningless.
;
; REPORT_MES_2
; On entry:
; BX contains the address of the control string.
; AX,DX contain a long integer.
; CX contains a word count for the %d argument in the control string
; or is meaningless.
;
;*************************************************************
;*****************************************************************************
; REPORT_MES_1 - Print the report messages. Display the file count and
; translate the number of clusters into the number of bytes.
;
; WARNING!! NOTE!! -->
;
; called by - PROCEDURE NAME
;
; inputs: AX - cluster count (1-ffff)
; BX - offset of control string
; CX -
; DX - high word of cluster count is zero'd out here.
; SP -
; BP -
; SI - low word of file count
; DI - hi word of file count
; DS - segment of control string
; ES -
;
; output: DISPLAY OF DATA TO SCREEN
;
; Regs abused - ALL
;
;logic: 1. zero out hi word of cluster count, and multiply by sectors per
; cluster. This gives number of sectors, which is a double word.
;
; 2. multiply by bytes per sector to give number of bytes.
;
; 3. place values in diplay fields, and call the msg. retriever.
;
;*****************************************************************************
report_mes_1:
push bx ;save it
xor dx,dx ;zero out hi word for multiply
mov cl,csize ;get sectors per cluster
xor ch,ch ;zero out hi byte of word
mul cx ;Convert cluster count to sector count ax/dx
mov bx,dx ;bx:ax is number to be mult;bgb
mov cx,ssize ;cx is number to mult with ;bgb
call multiply_32_bits ;bgb
mov dx,bx ;move hi value to dx
pop bx ;retore pointer;bgb
report_mes_2:
mov word ptr rarg1,ax ;Lo word of bytes in ax
mov word ptr rarg1+2,dx ;Hi word of bytes in dx
mov word ptr rarg3,si ;lo word of file count in si
mov word ptr rarg3+2,di ;hi word of file count in di
mov report_arg,bx ;Store the offset of the ctrl string
mov dx,bx ;dx has ptr to msg for disp_interface ;AC000;
call printf_crlf ;print msg, then carraige return
ret
PRINTF_CRLF:
call display_interface ; ;AC000;
DOCRLF: mov dx,offset dg:crlf_arg
call Display_Interface ;Replace old printf call with SysDispMsg;AN000;
ret ; ;AN000;
pathlabl chkdsk2
CODE ENDS
END


View File

@ -0,0 +1,206 @@
;fsexec equ true ; ; ;an038;bgb ;
FCB EQU 5CH
String_Done equ 0
No_Error equ 0
chk_Error equ 1
Stderr equ 2
FALSE EQU 0
TRUE EQU NOT FALSE
; NOTE WARNING DANGER.
; THIS EQU DEFINES AN OFFSET INTO THE SEARCH FCB OF THE LASTENT VALUE.
; ITS LOCATION MAY CHANGE FROM DOS VERSION TO DOS VERSION.
;2.0/2.1 value
;THISENT EQU 17H ;Relative entry number of current entry
;3.0 value
THISENT EQU 14H ;Relative entry number of current entry
;Attribute bits
RDONLY EQU 1
HIDDN EQU 2
SYSTM EQU 4
VOLIDA EQU 8
ISDIR EQU 10H
DRVCHAR EQU ":"
;
;*****************************************************************************
; Equates
;*****************************************************************************
;
Multiplex equ 2Fh ; ;AN000;
Set_Append_X equ 0B707h ; ;AN000;;
Append_X equ 0B706h ; ;AN000;;
Append_X_Set equ 1 ; ;AN000;
Append_Off equ 0 ; ;AN000;
Append_ON equ 1 ; ;AN000;
Disk_Error equ 80h ;INT 24h bit clear if disk error;AN000;
NO equ 0 ;AN000;
YES equ not NO ;AN000;
Year_Mask equ 0FE00h
Month_Mask equ 01E0h
Day_Mask equ 001Fh
Hour_Mask equ 0F800h
Minute_Mask equ 07E0h
Not_Include equ 0
Do_Include equ 1
YES_Found equ 1
NO_Found equ 0
ON equ 1
OFF equ 0
No_Ext_Attrib equ 0 ;AN000;
No_Entry equ 0
XA_Chain equ 84h ;Mark head of XA chain ;AN000;
ifdef fsexec ;an038;bgb
Len_FS_String_Buffer equ 13 ;an038;bgb
FAT12_File_System equ 01h ;an038;bgb;AN000;
FAT16_File_System equ 04h ;an038;bgb;AN000;
New_File_System equ 06h ;an038;bgb;AN000;
endif
Bad_Exit equ 0FFh ;Errorlevel = 0FFh ;AN000;
Net_Check equ 1200h ;AN000;
Assign_Check equ 8000h ;AN000;
Found_Yes equ 1 ;AN000;
Found_No equ 0 ;AN000;
Asciiz_End equ 0 ;AN000;
Dir_Attribute equ 10h
Vol_Attribute equ 08h
Dir_Entries_Per_Sector equ 512/32
Critical_Error_Fail equ 3
Write_Protect equ 0
Drive_Not_Ready equ 2
Blank equ " " ;AN000;
Head_Mask equ 7Fh ;Mask to turn off head bit ;AN000;
;Limits
BIG_FAT_THRESHOLD equ 4086 ;AN000;
;-------------------------------------------------------------------------------
; These are the data structures which we will need
;****************************************************************************
; Structures
;****************************************************************************
ifdef fsexec ;an038;bgb
Exec_Block_Parms struc ;an038;bgb
Segment_Env dw 0 ;an038;bgb
Offset_Command dw 0 ;an038;bgb
Segment_Command dw 0 ;an038;bgb
Offset_FCB1 dw 0 ;an038;bgb
Segment_FCB1 dw 0 ;an038;bgb
Offset_FCB2 dw 0 ;an038;bgb
Segment_FCB2 dw 0 ;an038;bgb
Exec_Block_Parms ends ;an038;bgb
Media_ID struc ;AN000;
Media_ID_Info_Level dw 0 ;AN000;
Media_ID_Serial_Number dd 0 ;AN000;
Media_ID_Volume_Label db 11 dup(" ") ;AN000;
Media_ID_File_System db 8 dup(" ") ;AN000;
Media_ID ends ;AN000;
endif ;an038;bgb
Sublist_Struc struc
Sublist_Size db ? ; ;AN000;
Sublist_Rsv db ? ; ;AN000;
Sublist_Offset dw ? ; ;AN000;
Sublist_Segment dw ? ; ;AN000;
Sublist_Number db ? ; ;AN000;
Sublist_Type db ? ; ;AN000;
Sublist_Max db ? ; ;AN000;
Sublist_Min db ? ; ;AN000;
Sublist_Char db ? ; ;AN000;
Sublist_Struc ends
A_DeviceParameters struc
SpecialFunctions db ? ;1 0
DeviceType db ? ;1 1
DeviceAttributes dw ? ;2 2
NumberOfCylinders dw ? ;2 4
MediaType db ? ;1 6
BytePerSector dw ? ;2 7
SectorsPerCluster db ? ;
ReservedSectors dw ?
NumberOfFATs db ?
RootEntries dw ?
TotalSectors dw ?
MediaDescriptor db ?
SectorsPerFAT dw ?
SectorsPerTrack dw ?
Heads dw ?
HiddenSectors dd ?
Ext_Total_Sectors dd ?
ReservedArea db 6 dup(?)
A_DeviceParameters ends
Relative_Sector_Buffer struc ; ;AN000;
Start_Sector_Low dw ? ;Low word of RBA sector ;AN000;
Start_Sector_High dw ? ;High word of RBA sector ;AN000;
Number_Sectors dw ? ;Number of sectors ;AN000;
Buffer_Offset dw ? ;Address of data buffer ;AN000;
Buffer_Segment dw ? ; ;AN000;
Relative_Sector_Buffer ends ; ;AN000;
XAL struc ;AN000;
XAL_Tsize dw ? ;AN000;
XAL_TCount dw ? ;AN000;
XAL_LSize dw ? ;AN000;
XAL_LCount dw ? ;AN000;
XAL_Data db 512-8 dup(?) ;AN000;
XAL ends ;AN000;
DIRENT STRUC
DB 7 DUP (?) ;Ext FCB junk
DB ? ;Drive
DIRNAM DB 11 DUP (?) ;
DIRATT DB ? ;
DIRCP DW ? ; ;AN000;
DIR_XA DW ? ; ;AN000;
DIRATT2 db ? ; ;AN000;
DIRRES DB 5 DUP (?) ; ;AC000;
DIRTIM DW ? ;
DIRDAT DW ? ;
DIRCLUS DW ? ;
DIRESIZ DD ? ;
DIRENT ENDS ;
ENTSIZ EQU SIZE DIRENT
;-------------------------------------------------------------------------------


File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,105 @@
BREAK MACRO subtitle
SUBTTL subtitle
PAGE
ENDM
;
;******************************************************************************
; Message Macro Definitions
;******************************************************************************
;
EXTRN Display_Interface:near
;-----------------------------------------------------------------------------
Message macro Message_Name ; ;AN000;
;
mov dx,offset dg:Message_Name ; ;AN000;
call Display_Interface ; ;AN000;
;
endm ; ;AN000;
;-----------------------------------------------------------------------------
Parse_Message macro ; ;AN000;
;
push ds
mov dx,dg
mov ds,dx
mov word ptr Parse_Error_Msg,ax ; ;AN000;
mov dx,offset dg:Parse_Error_Msg ; ;AN000;
call Display_Interface ; ;AN000;
pop ds ;
endm ; ;AN000;
;-----------------------------------------------------------------------------
Extended_Message macro ; ;AN000;
;
push ds
mov dx,dg
mov ds,dx
mov word ptr Extended_Error_Msg,ax ; ;AN000;
mov dx,offset dg:Extended_Error_Msg ; ;AN000;
call Display_Interface ; ;AN000;
pop ds
endm ; ;AN000;
;
;*****************************************************************************
; General Macro's
;*****************************************************************************
;
Procedure macro Proc_Name,Seg_Name ; ;AN000;
;
Public Proc_Name ; ;AN000;
Proc_Name proc ; ;AN000;
endm ; ;AN000;
;-----------------------------------------------------------------------------
DOS_Call macro Function ; ;AN000;
;
mov ah,Function ; ;AN000;
int 21h ; ;AN000;
;
endm ; ;AN000;
;-----------------------------------------------------------------------------
Popff macro
Assume cs:DG
jmp $+3
iret
push cs
call $-2
Assume cs:code
endm
;-----------------------------------------------------------------------------
Set_Data_Segment macro
push ax
mov ax,dg ;Point to data segment
mov ds,ax ;
push ds
pop es
pop ax
.LALL
assume ds:dg,es:dg
.XALL
endm


File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,285 @@
;an000;bgb
;an000;bgb
;an000;bgb
;an000;bgb
data segment public para 'DATA' ;an000;bgb ;AN000;
;an000;bgb
;an000;bgb
; ;an000;bgb
;***************************************************************************** ;an000;bgb
; Publics ;an000;bgb
;***************************************************************************** ;an000;bgb
; ;an000;bgb
;an000;bgb
; Public Drive_Letter_Buffer ;an000;bgb
Public SwBuffer ;an000;bgb
Public Switch_F_Buffer ;an000;bgb
; Public FileSpec_Buffer ;an000;bgb
public buffer ;an000;bgb
public sw_v, sw_f ;an000;bgb;an020;bgb
;an000;bgb
; ;an000;bgb
;*************************************************************************** ;an000;bgb
; Equates ;an000;bgb
;*************************************************************************** ;an000;bgb
; ;an000;bgb
;an000;bgb
;Match Flags ;an000;bgb
;an000;bgb
Numeric_Value equ 8000h ; ;an000;bgb;AN000;
Signed_Numeric_Value equ 4000h ; ;an000;bgb;AN000;
Simple_String equ 2000h ; ;an000;bgb;AN000;
Date_String equ 1000h ; ;an000;bgb;AN000;
Time_String equ 0800h ; ;an000;bgb;AN000;
Complex_List equ 0400h ; ;an000;bgb;AN000;
Quoted_String equ 0080h ; ;an000;bgb;AN000;
Ignore_Colon equ 0010h ; ;an000;bgb;AN000;
Repeats_Allowed equ 0002h ; ;an000;bgb;AN000;
Optional equ 0001h ; ;an000;bgb;AN000;
Filespec equ 0200h ; ;an000;bgb;AN000;
Drive_Only equ 0100h ; ;an000;bgb;AN000;
;an000;bgb
;Function_Flags ;an000;bgb
;an000;bgb
File_Table_Capitalize equ 1 ; ;an000;bgb;AN000;
Char_Table_Capitalize equ 2 ; ;an000;bgb;AN000;
Remove_Colon equ 10h ; ;an000;bgb;AN000;
;an000;bgb
;Extra delimeters and EOL ;an000;bgb
;an000;bgb
Delimiters_Only equ 1 ; ;an000;bgb;AN000;
EOL_Or_Delimiters equ 2 ; ;an000;bgb;AN000;
;an000;bgb
Semi_Colon equ ";" ; ;an000;bgb;AN000;
Tab equ 09h ; ;an000;bgb;AN000;
Colon equ ":" ; ;an000;bgb;AN000;
;an000;bgb
;an000;bgb
;Parse Errors ;an000;bgb
;an000;bgb
No_Error equ 0 ; ;an000;bgb;AN000;
Too_Many_Operands equ 1 ; ;an000;bgb;AN000;
Operand_Missing equ 2 ; ;an000;bgb;AN000;
Not_In_Switch_List equ 3 ; ;an000;bgb;AN000;
Not_In_Keyword_List equ 4 ; ;an000;bgb;AN000;
Out_Of_Range equ 6 ; ;an000;bgb;AN000;
Not_In_Value_List equ 7 ; ;an000;bgb;AN000;
Not_In_String_List equ 8 ; ;an000;bgb;AN000;
Syntax_Error equ 9 ; ;an000;bgb;AN000;
End_Of_Parse equ -1 ; ;an000;bgb;AN000;
;an000;bgb
;Return types ;an000;bgb
;an000;bgb
Type_Reserved equ 0 ; ;an000;bgb;AN000;
Type_Number equ 1 ; ;an000;bgb;AN000;
Type_List_Index equ 2 ; ;an000;bgb;AN000;
Type_String equ 3 ; ;an000;bgb;AN000;
Type_Complex equ 4 ; ;an000;bgb;AN000;
Type_Filespec equ 5 ; ;an000;bgb;AN000;
Type_Drive equ 6 ; ;an000;bgb;AN000;
Type_Date equ 7 ; ;an000;bgb;AN000;
Type_Time equ 8 ; ;an000;bgb;AN000;
Type_Quoted_String equ 9 ; ;an000;bgb;AN000;
;an000;bgb
;Other ;an000;bgb
;an000;bgb
None equ 0 ; ;an000;bgb;AN000;
No_Error equ 0 ; ;an000;bgb;AN000;
Switch_Found equ 0FFFFh ; ;an000;bgb;AN000;
Range_Ok equ 1 ; ;an000;bgb;AN000;
Command_Line_Parms equ 81h ; ;an000;bgb;AN000;
;an000;bgb
; ;an000;bgb
;***************************************************************************** ;an000;bgb
; Parse Structures ;an000;bgb
;***************************************************************************** ;an000;bgb
; ;an000;bgb
;an000;bgb
Control struc ;an000;bgb
;an000;bgb
Match_Flags dw ? ;an000;bgb
Function_Flags dw ? ;an000;bgb
Result dw ? ;an000;bgb
Values dw ? ;an000;bgb
Num_Keywords db ? ;an000;bgb
Keyword db ? ;an000;bgb
;an000;bgb
Control ends ;an000;bgb
;an000;bgb
;Drive_Letter_Return struc ; ;an000;bgb ;AN000;
;Drive_Type db 0 ; ;an000;bgb ;AN000;
;Drive_Item_Tag db 0 ; ;an000;bgb ;AN000;
;Drive_Pointer dw 0 ; ;an000;bgb ;AN000;
;Drive_Number db 0 ;A=1, B=2, C=3 ;an000;bgb ;AN000;
;Drive_debug db 8 dup(0) ;an000;bgb
;Drive_Letter_Return ends ; ;an000;bgb ;AN000;
; ;an000;bgb
;Filespec_Return struc ;AN000;SM ;an000;bgb
;Filespec_Type db 0 ;AN000;SM ;an000;bgb
;FileSpec_Item db 0 ;AN000;SM ;an000;bgb
;FileSpec_Pointer dw 0 ;AN000;SM ;an000;bgb
;Filespec_String_Off dw 0 ;AN000;SM ;an000;bgb
;FileSpec_String_Seg dw 0 ;an000;bgb
;FileSpec_Return ends ;an000;bgb
;an000;bgb
single_Return struc ;AN000;SM ;an000;bgb
dftype db 0 ;AN000;SM ;an000;bgb
Item db 0 ;AN000;SM ;an000;bgb
Pointer dw 0 ;AN000;SM ;an000;bgb
drnum_stroff dw 0 ;AN000;SM ;an000;bgb
return_strseg dw 0 ;an000;bgb
single_return ends ;an000;bgb
;an000;bgb
;an000;bgb
Switch_Return struc ; ;an000;bgb;AN000;
Switch_Type db 0 ; ;an000;bgb;AN000;
Switch_Item_Tag db 0 ; ;an000;bgb;AN000;
Switch_Pointer dw 0 ; ;an000;bgb;AN000;
Switch_Debug db 4 dup(0) ;an000;bgb
Switch_Return ends ; ;an000;bgb;AN000;
;an000;bgb
Switch_Num_Return struc ; ;an000;bgb;AN000;
Switch_Num_Type db 0 ; ;an000;bgb ;AN000;
Switch_Num_Item_Tag db 0 ; ;an000;bgb ;AN000;
Switch_Num_Pointer dw 0 ; ;an000;bgb ;AN000;
Switch_Number_Low dw 0 ; ;AN0;an000;bgb00;
Switch_Number_High dw 0 ; ;AN0;an000;bgb00;
Switch_Num_Return ends ; ;an000;bgb;AN000;
;an000;bgb
Switch_String_Return struc ; ;an000;bgb;AN000;
Switch_String_Type db 0 ; ;an000;bgb ;AN000;
Switch_String_Item_Tag db 0 ; ;an000;bgb ;AN000;
Switch_String_Pointer dw 0 ; ;an000;bgb ;AN000;
Switch_String_Off dw 0 ; ;an000;bgb;AN000;
Switch_String_Seg dw 0 ; ;an000;bgb;AN000;
Switch_String_Return ends ; ;an000;bgb;AN000;
;an000;bgb
;an000;bgb
; ;an000;bgb
;************************************************************************** ;an000;bgb
; Parse tables ;an000;bgb
;************************************************************************** ;an000;bgb
; ;an000;bgb
Public input_Table ;an000;bgb
input_Table label byte ; ;AN000;;an000;bgb
;an000;bgb
dw offset dg:ext_table ;Point to next level ;A;an000;bgbN000;
db Delimiters_Only ; ;an000;bgb;AN000;
db 1 ; ;an000;bgb;AN000;
db Semi_Colon ; ;an000;bgb;AN000;
;an000;bgb
Drive_Table label byte ;an000;bgb;AN000;
; ;an000;bgb
dw offset dg:Drive_Control_Definition ;Point to next level ;an000;bgb ;AN000;
db Delimiters_Only ; ;an000;bgb;AN000;
db 1 ; ;an000;bgb;AN000;
db Semi_Colon ; ;an000;bgb;AN000;
;an000;bgb
; ;an000;bgb
;************************************************************************** ;an000;bgb
;Define Positionals, Switches and Keywords ;an000;bgb
;************************************************************************** ;an000;bgb
; ;an000;bgb
;an000;bgb
Public ext_table ;an000;bgb
ext_table label byte ; ;an000;bgb;AN000;
; ;an000;bgb
db 0,1 ;up to one parm, either drive or file ;an000;bgb;an026;bgb
dw dg:dfcontrol ;Pointer to control table ;an000;bgb ;AN000;
db 1 ;1 switch def ;an000;bgb;AN020;bgb
dw dg:SwControl ;switch control block ;an000;bgb;AN020;bgb
db None ;No Keywords (maxk) ;an000;bgb;AN000;
; ;an000;bgb
Drive_Control_Definition label byte ; ;an000;bgb;AN000;
; ;an000;bgb
db 0,1 ;Only drive letter positional ;an000;bgb;AN000;
dw dg:dfControl ;Pointer to control table ;AN0;an000;bgb00;
db None ;0 switches ;an000;bgb;AN000;
db None ;No Keywords (maxk) ;an000;bgb;AN000;
; ;an000;bgb
;an000;bgb
;an000;bgb
; ;an000;bgb
;************************************************************************** ;an000;bgb
; Define Positionals, Switches and Keywords ;an000;bgb
;************************************************************************** ;an000;bgb
; ;an000;bgb
;this is the new control block for both drive letters and filespecs ;an000;bgb
Public dfControl ;an000;bgb
dfControl label byte ; ;AN000;;an000;bgb
dw drive_only+FileSpec+Optional ; ;an000;bgb ;AN000;
dw None ; ;an000;bgb;AN000;
dw dg:Buffer ; ;AN000; ;an000;bgb
dw dg:No_Value ; ;an000;bgb;AN000;
db None ; ;an000;bgb;AN000;
;an000;bgb
Public SwControl ;an02;an000;bgb0;bgb
SwControl label byte ; ;AN020;;an000;bgbbgb
dw None ; ;an000;bgb;AN000;
dw None ; ;an000;bgb;AN000;
dw dg:SwBuffer ; ;AN000;;an000;bgb
dw dg:No_Value ;an000;bgb ;AN000;
db 2 ; ;an000;bgb;AN020;bgb
sw_v db "/V",0 ; ;an000;bgb;AN020;bgb
sw_f db "/F",0 ; ;an000;bgb;AN020;bgb
; ;an000;bgb
;an000;bgb
; ;an000;bgb
;***************************************************************************** ;an000;bgb
; Value lists ;an000;bgb
;***************************************************************************** ;an000;bgb
; ;an000;bgb
;an000;bgb
No_Value db 0 ; ;an000;bgb;AN000;
;an000;bgb
;an000;bgb
; ;an000;bgb
;************************************************************************ ;an000;bgb
; PARSE Return Buffers ;an000;bgb
;************************************************************************ ;an000;bgb
; ;an000;bgb
; these buffers were replaced by a single buffer due to the parser bug ;an000;bgb
;Drive_Letter_Buffer Drive_Letter_Return <> ;Example of structure ;an000;bgb ;AN000;
;FileSpec_Buffer FileSpec_Return <> ; ;an000;bgb
SwBuffer Switch_Return <> ; ;an000;bgb;AN000;
Switch_F_Buffer Switch_Return <> ; ;an000;bgb;AN000;
buffer single_return <> ; new results buffer ;an000;bgb
data ends ; ;an000;bgb;AN000;
;an000;bgb
; ;an000;bgb
;***************************************************************************** ;an000;bgb
; SysParse Routines ;an000;bgb
;***************************************************************************** ;an000;bgb
; ;an000;bgb
;an000;bgb
;an000;bgb
code segment public para 'CODE' ;an000;bgb
;an000;bgb
FarSW equ Not_Include ; ;an000;bgb;AN000; ;AN000;
DateSW equ Not_Include ; ;an000;bgb;AN000;
TimeSW equ Not_Include ; ;an000;bgb;AN000;
FileSW equ Do_Include ; ;an000;bgb;AN000;
CAPSW equ Not_Include ; ;an000;bgb;AN000;
CmpxSW equ Not_Include ; ;an000;bgb;AN000;
NumSW equ Not_Include ; ;an000;bgb;AN000;
KeySW equ Not_Include ; ;an000;bgb;AN000;
SwSW equ Do_Include ; ;an000;bgb;AN000;
Val1SW equ Not_Include ; ;an000;bgb;AN000;
Val2SW equ Not_Include ; ;an000;bgb;AN000;
Val3SW equ Not_Include ; ;an000;bgb;AN000;
DrvSW equ Do_Include ; ;an000;bgb;AN000;
QusSW equ Not_Include ; ;an000;bgb;AN000;
basesw equ 1 ;use ds as the default register ;an025;bgb
incsw equ 0 ;include psdata myself ;an028;bgb
code ends ;an028;bgb
data segment PUBLIC para 'DATA' ;an028;bgb
include psdata.inc ;an028;bgb
data ends ;an028;bgb
code segment PUBLIC para 'CODE' ;an028;bgb
pathlabl parser ;an028;bgb
INCLUDE PARSE.ASM ;AN000; ;an028;bgb
pathlabl parser ;an028;bgb
code ends ;an000;bgb

View File

@ -0,0 +1,93 @@
TITLE CHKPRMT - Procedures called from chkdsk which prompt ;an000;bgb
page ,132 ; ;an000;bgb
;an000;bgb
.xlist ;an000;bgb
include chkseg.inc ;an000;bgb
INCLUDE CHKCHNG.INC ;an000;bgb
INCLUDE SYSCALL.INC ;an000;bgb
INCLUDE CHKEQU.INC ;an000;bgb
INCLUDE CHKMACRO.INC ;an000;bgb
include pathmac.inc ;an000;bgb
.list ;an000;bgb
;an000;bgb
;an000;bgb
CONST SEGMENT PUBLIC PARA 'DATA' ;an000;bgb
EXTRN YES_BYTE:BYTE,NO_BYTE:BYTE ;an000;bgb
EXTRN YN_ARG:WORD ;an000;bgb
EXTRN HECODE:byte,CONBUF:byte ;an000;bgb
CONST ENDS ;an000;bgb
;an000;bgb
;an000;bgb
CODE SEGMENT PUBLIC PARA 'CODE' ;an000;bgb
ASSUME CS:DG,DS:DG,ES:DG,SS:DG ;an000;bgb
EXTRN PRINTF_CRLF:NEAR,DOCRLF:NEAR ;an000;bgb
;an000;bgb
pathlabl chkprmt ;an000;bgb
;***************************************************************************** ;an000;bgb
;Routine name:PromptYN ;an000;bgb
;***************************************************************************** ;an000;bgb
; ;an000;bgb
;description: Validate that input is valid Y/N for the country dependent info ;an000;bgb
; Return Z flag if 'Y' entered ;an000;bgb
;Called Procedures: Message (macro) ;an000;bgb
; User_String ;an000;bgb
; ;an000;bgb
;Change History: Created 5/10/87 MT ;an000;bgb
; ;an000;bgb
;Input: DX = offset to message ;an000;bgb
; ;an000;bgb
;Output: Z flag if 'Y' entered ;an000;bgb
; ;an000;bgb
;Psuedocode ;an000;bgb
;---------- ;an000;bgb
; ;an000;bgb
; DO ;an000;bgb
; Display prompt and input character ;an000;bgb
; IF got character ;an000;bgb
; Check for country dependent Y/N (INT 21h, AX=6523h Get Ext Country;an000;bgb)
; IF NC (Yes or No) ;an000;bgb
; Set Z if Yes, NZ if No ;an000;bgb
; ENDIF ;an000;bgb
; ELSE (nothing entered) ;an000;bgb
; stc ;an000;bgb
; ENDIF ;an000;bgb
; ENDDO NC ;an000;bgb
; ret ;an000;bgb
;***************************************************************************** ;an000;bgb
Procedure PromptYN ; ;an000;bgb;AN000;
push si ;Save reg ;an000;bgb
; $DO ; ;an000;bgb;AC000;
$$DO1:
Call Display_Interface ;Display the message ;an000;bgb;AC000;
MOV DX,OFFSET DG:CONBUF ;Point at input buffer ;an000;bgb
DOS_Call Std_Con_String_Input ;Get input ;an000;bgb;AC000;
CALL DOCRLF ; ;an000;bgb
MOV SI,OFFSET DG:CONBUF+2 ;Point at contents of buffer ;an000;bgb
CMP BYTE PTR [SI-1],0 ;Was there input? ;an000;bgb
; $IF NE ;Yep ;an000;bgb;AC000;
JE $$IF2
mov al,23h ;See if it is Y/N ;an000;bgb;AN000;
mov dl,[si] ;Get character ;an000;bgb;AN000;
DOS_Call GetExtCntry ;Get country info call ;an000;bgb;AN000;
; $IF NC ;Yes or No entered ;an000;bgb;AN000;
JC $$IF3
cmp ax,Yes_Found ;Set Z if Yes, NZ if No ;an000;bgb;AN000;
clc ;CY=0 means Y/N found ;an000;bgb
; $ENDIF ;CY set if neither ;an000;bgb;AN000;
$$IF3:
; $ELSE ;No characters input ;an000;bgb
JMP SHORT $$EN2
$$IF2:
stc ;CY means not Y/N ;an000;bgb
; $ENDIF ; ;an000;bgb
$$EN2:
; $ENDDO NC ; ;an000;bgb;AN000;
JC $$DO1
pop si ; ;an000;bgb
ret ; ;an000;bgb
PromptYN endp ; ;an000;bgb;AN000;
pathlabl chkprmt ;an000;bgb
;an000;bgb
CODE ENDS ;an000;bgb
END ;an000;bgb


File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,479 @@
TITLE CHKPROC2 - PART2 Procedures called from chkdsk
page ,132 ;
.xlist
include chkseg.inc ;an005;bgb
INCLUDE CHKCHNG.INC
INCLUDE DOSSYM.INC
INCLUDE CHKEQU.INC
INCLUDE CHKMACRO.INC
include pathmac.inc
CONST SEGMENT PUBLIC PARA 'DATA'
EXTRN FIXMES_ARG:word ;an049;bgb
EXTRN FATAL_ARG:word
EXTRN BADW_ARG:word,FATAL_END:word
EXTRN badrw_num:word,BADRW_STR:WORD,HAVFIX:byte
EXTRN DIRTYFAT:byte,CROSSCNT:dword,DOFIX:byte,SECONDPASS:byte
EXTRN BADSIZ:word,ORPHSIZ:word,ORPHFCB:byte
EXTRN HECODE:byte,USERDIR:byte,FRAGMENT:byte
EXTRN ORPHEXT:byte,ALLDRV:byte,FIXMFLG:byte,DIRCHAR:byte
EXTRN EOFVAL:word,BADVAL:word
extrn fTrunc:BYTE
CONST ENDS
DATA SEGMENT PUBLIC PARA 'DATA'
extrn fatcnt:byte, orph_arg:word ;an005;bgb;an049;bgb
EXTRN THISDPB:dword,NUL_ARG:byte
EXTRN NAMBUF:byte,SRFCBPT:word,FATMAP:word
EXTRN MCLUS:word,CSIZE:byte,SSIZE:word
EXTRN DSIZE:word,ARG_BUF:byte,ERRCNT:byte
EXTRN USERDEV:byte,HARDCH:dword,CONTCH:dword
EXTRN ExitStatus:Byte,Read_Write_Relative:Byte
extrn bytes_per_sector:word ;an005;bgb
extrn fattbl_seg:word, fatsiz:word, paras_per_fat:word ;an005;bgb
extrn fatmsg1:word ;an024;bgb
extrn fatmsg2:word ;an024;bgb
EXTRN dbcs_vector:byte ;an055;bgb
EXTRN dbcs_vector_off:word ;an055;bgb
EXTRN dbcs_vector_seg:word ;an055;bgb
DATA ENDS
CODE SEGMENT PUBLIC PARA 'CODE'
ASSUME CS:DG,DS:DG,ES:DG,SS:DG
EXTRN PRINTF_CRLF:NEAR,FCB_TO_ASCZ:NEAR
EXTRN PROMPTYN:NEAR,DIRPROC:NEAR
EXTRN DOCRLF:NEAR,UNPACK:NEAR,PACK:NEAR
EXTRN CHECKNOFMES:NEAR
EXTRN multiply_32_bits:near ;an047;bgb
extrn nowrite:near, done:near, pack:near, unpack:near
extrn promptrecover:near, findchain:near
public RECOVER, DoAsk
public MAKORPHNAM, NAM0, NAMMADE
public GETFILSIZ, NCLUS, GOTEOF, CHKCROSS, RET8
public FATAL, hav_fatal_arg, INT_23, RDONE
public Systime ;an005;bgb
public int_24 ;an005;bgb
public CHECK_DBCS_CHARACTER ;an055;bgb
.list
pathlabl chkproc2
;*****************************************************************************
; RECOVER -
; free orphans or do chain recovery. Note that if we have NOT been able to
; process the entire tree (due to inability to CHDIR), we temporarily set
; DoFix to FALSE, do the operation, and then reset it.
;
; inputs: si - total number of clusters
; es - points to fatmap
;
; outputs: orphaned clusters are converted to files
; LOGIC
; - display dont fix msg if appropriate
; - display number of lost clusters
; - ask the user if he wants the chains converted to files
;***************************************************************************
RECOVER:
mov al,1
xchg al,[fixmflg]
or al,al
; $IF Z ; where there any errors found?
JNZ $$IF1
cmp [dofix],0 ; yes - is the /f flag off?
; $IF Z ; yes - display the dont fix msg
JNZ $$IF2
mov dx,offset dg:FIXMES_arg
CALL PRINTf_crlf
call DoCRLF ; ;AN000;
; $ENDIF
$$IF2:
; $ENDIF
$$IF1:
CALL DOCRLF
CHAINREPORT:
;;;;mov si,orphsiz ;get number of bad clusters found (recover) ;an005;bgb;an049;bgb
;;;;mov [orph_num],si ; Prints "XXX lost clusters found in YYY chains.";an049;bgb
call findchain ; On entry SI is the XXX value and the YYY value is
mov dx,offset dg:orph_arg ; in orphan-count.
call printf_crlf
TEST fTrunc,-1
; $IF NZ
JZ $$IF5
XOR AX,AX ; We have truncated the scan. Set DoFix to FALSE,
XCHG AL,DoFix ; do the operation and then restore things.
PUSH AX
CALL PromptRecover
POP AX
MOV DoFix,AL
DoAsk:
; $ELSE
JMP SHORT $$EN5
$$IF5:
CALL PromptRecover
; $ENDIF
$$EN5:
return
;*****************************************************************************
;*****************************************************************************
MAKORPHNAM:
PUSH SI
MOV SI,OFFSET DG:ORPHEXT - 1
NAM0:
INC BYTE PTR [SI]
CMP BYTE PTR [SI],'9'
JLE NAMMADE
MOV BYTE PTR [SI],'0'
DEC SI
JMP NAM0
NAMMADE:
POP SI
RET
;*****************************************************************************
; GETFILSIZ - calculate the file size based on the number of clusters.
;
; WARNING!! NOTE!! -->
;
; called by - PROCEDURE NAME
;
; inputs: AX -
; BX -
; CX -
; DX -
; SP -
; BP -
; SI - conatins the starting cluster number
; DI -
; DS -
; ES -
;
; output: AX - low word of the file size
; BX -
; CX -
; DX - hi word of the file size
; SP -
; BP -
; SI -
; DI -
; DS -
; ES -
;
; Regs abused - none
;
;logic: 1. save bx & cx for 32 bit mul
;
; 2. zero out file size results
;
; 3. do for all clusters:
;
; 4. get the next one and inc cluster counter
;
; 5. multiply clusters times sectors per cluster to give
; number of sectors in file. This can be a 2 word value - DX:AX.
;
; 6. multiply the sectors times the number of bytes per sector. This
; yields the number of bytes in the file.
;*****************************************************************************
;SI is start cluster, returns filesize as DX:AX
Procedure getfilsiz,near
savereg <bx,cx>
XOR AX,AX ;zero out low word
XOR DX,DX ;zero out high word
OR SI,SI ;did we get a zero cluster?
; $if NZ
JZ $$IF8
; $DO ;do for all clusters
$$DO9:
NCLUS: CALL UNPACK ;find the next cluster
XCHG SI,DI ;put output into input for unpack
INC AX ;found another cluster
CMP SI,[EOFVAL] ;did we find last cluster?
; $leave ae ;yes, so exit loop
JAE $$EN9
;;;;;;;CMP SI,2
;;;;;;;JAE NCLUS
; $enddo
JMP SHORT $$DO9
$$EN9:
GOTEOF:
MOV BL,[CSIZE] ;get sectors per cluster
XOR BH,BH
MUL BX ;clusters * secs/cluster = sectors
mov bx,dx ;get high num for 32bit mult
mov cx,ssize ;cx = word to mult with
call multiply_32_bits ;mul bx:ax * cx
mov dx,bx ;save high word
; $endif
$$IF8:
restorereg <bx,cx>
return
EndProc getfilsiz
;*****************************************************************************
;*****************************************************************************
Public Chkcross
CHKCROSS:
;Check for Crosslinks, do second pass if any to find pairs
MOV SI,word ptr CROSSCNT
cmp word ptr crosscnt,0 ;if there is at least one crossed
; $if nz,or
JNZ $$LL13
cmp word ptr crosscnt+2,0
; $if nz
JZ $$IF13
$$LL13:
CALL DOCRLF ;display another line
MOV SecondPass,True ; ; ;AC000;
XOR AX,AX ;
PUSH AX
PUSH AX
CALL DIRPROC ;Do it again
; $endif
$$IF13:
RET8: RET
;*****************************************************************************
;*****************************************************************************
FATAL:
;Unrecoverable error
mov dx,offset dg:FATAL_arg
mov [fatmsg1],bx ;an024;bgb
cmp byte ptr [nul_arg],0
jnz hav_fatal_arg
mov [fatmsg2],offset dg:fatal_end
hav_fatal_arg:
CALL PRINTf_crlf
MOV DL,[USERDEV] ;At least leave on same drive
DOS_Call Set_Default_Drive ; ;AC000;
;MOV AH,EXIT
mov ExitStatus,Bad_Exit ;Get return code ;AC000;
;INT 21H
ret ;Ret Main_Init for common exit
;*****************************************************************************
;*****************************************************************************
iNT_24 PROC FAR
aSSUME DS:NOTHING,ES:NOTHING,SS:NOTHING
PUSHF
push ax ;Save AX register ;AN000;
test al,Disk_Error ;Is it a disk critical err?
; $IF Z ;Yes
JNZ $$IF15
mov ax,di ;Get error (DI low) ;AN000;
cmp al,Write_Protect ;Special case errors ;AN000;
; $IF E,OR ;If write protect or ;AN000;
JE $$LL16
cmp al,Drive_Not_Ready ; if drive not ready ;AN000;
pop ax ;Balance stack again ;AN000;
; $IF E ; ;AN000;
JNE $$IF16
$$LL16:
CALL dword ptr HardCh ; let parent's handler decide what to do
; $ELSE ;Other error ;AN000;
JMP SHORT $$EN16
$$IF16:
pop ax ;balance stack ;AN000;
mov al,Critical_Error_Fail ;Fail the operation ;AN000;
; $ENDIF ; ;AN000;
$$EN16:
; $ELSE ;Not disk error
JMP SHORT $$EN15
$$IF15:
CALL dword ptr HardCh ; let parent's handler decide what to do
; $ENDIF
$$EN15:
CMP AL,2 ;Abort? ;AC000;
; $IF E ;Yes ;AC000;
JNE $$IF21
STI ;Turn off Interrupts
CALL DONE ;Forget about directory, restore users drive
mov ExitStatus,Bad_Exit ;Get return code ;AN000;
; $ENDIF ;AN000;
$$IF21:
IRET
iNT_24 ENDP
;*****************************************************************************
;*****************************************************************************
INT_23 proc far
STI
LDS DX,[HARDCH]
mov al,24h ; ;AC000;
DOS_Call Set_Interrupt_Vector ; ;AC000;
LDS DX,cs:[CONTCH] ;ac039;bgb
mov al,23h ; ;AC000;
DOS_Call Set_Interrupt_Vector ; ;AC000;
PUSH CS
POP DS
ASSUME DS:DG
MOV [FRAGMENT],0
RDONE:
CALL NOWRITE ;Restore users drive and directory
;MOV AH,EXIT
;MOV AL,0FFH
;INT 21H
mov ExitStatus,Bad_Exit ;Get return code ;AC000;
stc
ret ;Ret for common exit ;AN000;
int_23 endp
;*****************************************************************************
;*****************************************************************************
;
; Systime returns the current date in AX, current time in DX
; AX - HHHHHMMMMMMSSSSS hours minutes seconds/2
; DX - YYYYYYYMMMMDDDDD years months days
;
public Systime
Systime:
DOS_Call Get_Time ; ;AC000;
SHL CL,1 ;Minutes to left part of byte
SHL CL,1
SHL CX,1 ;Push hours and minutes to left end
SHL CX,1
SHL CX,1
SHR DH,1 ;Count every two seconds
OR CL,DH ;Combine seconds with hours and minutes
MOV DX,CX
PUSH DX ; Save time
;
; WARNING! MONTH and YEAR must be adjacently allocated
;
DOS_Call Get_Date ; ;AC000;
SUB CX, 1980
MOV AX, CX
MOV CL, 4
SHL AL, CL ; Push year to left for month
OR AL, DH ; move in month
MOV CL,4
SHL AX,CL ;Push month to left to make room for day
SHL AX,1
OR AL, DL
POP DX ; Restore time
XCHG AX, DX ; Switch time and day
return
;***************************************************************************** ;an055;bgb
;Routine name: Check_DBCS_CharACter ;an055;bgb
;***************************************************************************** ;an055;bgb
; ;an055;bgb
;Description: Check if specified byte is in rANges of DBCS vectors ;an055;bgb
; ;an055;bgb
;Called Procedures: None ;an055;bgb
; ;an055;bgb
;ChANge History: Created 6/12/87 MT ;an055;bgb
; ;an055;bgb
;Input: AL = CharACter to check for DBCS lead charACter ;an055;bgb
; DBCS_Vector = YES/NO ;an055;bgb
; ;an055;bgb
;Output: CY set if DBCS charACter ;an055;bgb
; DBCS_VECTOR = YES ;an055;bgb
; ;an055;bgb
; ;an055;bgb
;Psuedocode ;an055;bgb
;---------- ;an055;bgb
; Save registers ;an055;bgb
; IF DBCS vector not found ;an055;bgb
; Get DBCS environmental vector (INT 21h ;an055;bgb
; Point at first set of vectors ;an055;bgb
; ENDIF ;an055;bgb
; SEARCH ;an055;bgb
; LEAVE End of DBCS vectors ;an055;bgb
; EXITIF CharACter > X1,AND (X1,Y1) are environment vectors ;an055;bgb
; EXITIF CharACter < Y1 ;an055;bgb
; STC (DBCS charACter) ;an055;bgb
; ORELSE ;an055;bgb
; Inc pointer to next set of vectors ;an055;bgb
; ENDLOOP ;an055;bgb
; CLC (Not DBCS charACter) ;an055;bgb
; ENDSRCH ;an055;bgb
; Restore registers ;an055;bgb
; ret ;an055;bgb
;***************************************************************************** ;an055;bgb
DBCS_Vector_Size equ 2 ;an055;bgb
end_of_vector equ 0 ;an055;bgb
Procedure Check_DBCS_Character ; ;an055;bgb
push ds ;Save registers ;an055;bgb
push si ; " " " " ;an055;bgb
push ax ; " " " " ;an055;bgb
;;;;;;;;push ds ; " " " " ;an055;bgb
;;;;;;;;pop es ;Establish addressability ;an055;bgb
cmp byte ptr es:DBCS_VECTOR,Yes ;Have we set this yet? ;an055;bgb
; $IF NE ;Nope ;an055;bgb
JE $$IF23
push ax ;Save input charACter ;an055;bgb
mov al,0 ;Get DBCS environment vectors ;an055;bgb
DOS_Call Hongeul ; " " " " ;an055;bgb
mov byte ptr es:DBCS_VECTOR,YES ;Indicate we've got vector ;an055;bgb
mov es:DBCS_Vector_Off,si ;Save the vector ;an055;bgb
mov ax,ds ; ;an055;bgb
mov es:DBCS_Vector_Seg,ax ; ;an055;bgb
pop ax ;Restore input charACter ;an055;bgb
; $ENDIF ; for next time in ;an055;bgb
$$IF23:
mov si,es:DBCS_Vector_Seg ;Get saved vector pointer ;an055;bgb
mov ds,si ; ;an055;bgb
mov si,es:DBCS_Vector_Off ; ;an055;bgb
; $SEARCH ;Check all the vectors ;an055;bgb
$$DO25:
cmp word ptr ds:[si],End_Of_Vector ;End of vector table? ;an055;bgb
; $LEAVE E ;Yes, done ;an055;bgb
JE $$EN25
cmp al,ds:[si] ;See if char is in vector ;an055;bgb
; $EXITIF AE,AND ;If >= to lower, ANd ;an055;bgb
JNAE $$IF25
cmp al,ds:[si+1] ; =< thAN higher rANge ;an055;bgb
; $EXITIF BE ; then DBCS charACter ;an055;bgb
JNBE $$IF25
stc ;Set CY to indicate DBCS ;an055;bgb
; $ORELSE ;Not in rANge, check next ;an055;bgb
JMP SHORT $$SR25
$$IF25:
add si,DBCS_Vector_Size ;Get next DBCS vector ;an055;bgb
; $ENDLOOP ;We didn't find DBCS char ;an055;bgb
JMP SHORT $$DO25
$$EN25:
clc ;Clear CY for exit ;an055;bgb
; $ENDSRCH ; ;an055;bgb
$$SR25:
pop ax ;Restore registers ;an055;bgb
pop si ; " " " " ;an055;bgb
pop ds ;Restore data segment ;an055;bgb
ret ; ;an055;bgb
Check_DBCS_CharACter endp ; ;an055;bgb
pathlabl chkproc2
CODE ENDS
END


View File

@ -0,0 +1,21 @@
PSP segment public para 'DUMMY' ;an000;bgb
PSP ends ;an000;bgb
;an000;bgb
data segment public para 'DATA' ;an000;bgb
data ends ;an000;bgb
;an000;bgb
CONST SEGMENT PUBLIC para 'DATA' ;an000;bgb
CONST ENDS ;an000;bgb
;an000;bgb
code segment public para 'CODE' ;an000;bgb
code ends ;an000;bgb
;an000;bgb
cstack segment para stack 'STACK' ;an000;bgb
cstack ends ;an000;bgb
;an000;bgb
lastseg segment public para 'LAST' ;an000;bgb;AN000;bgb
lastseg ends ;this is a pointer to the end of the pgm ;A;an000;bgbN000;bgb
;an000;bgb;AN000;bgb
DG GROUP data,const,code,CSTACK,lastseg ;an000;bgb
assume cs:dg,ds:dg,ss:dg,es:dg ;an000;bgb


View File

@ -0,0 +1,94 @@
#************************** makefile for cmd\append ***************************
msg =..\..\messages
dos =..\..\dos
inc =..\..\inc
hinc =..\..\h
#
####################### dependencies begin here. #########################
#
all: chkdsk.com
chkdsk.ctl: chkdsk.skl \
makefile \
$(msg)\$(COUNTRY).msg
chkinit.obj: chkinit.asm \
chkequ.inc chkmacro.inc chkparse.inc chkchng.inc \
makefile chkseg.inc \
$(inc)\ioctl.inc
chkdsk1.obj: chkdsk1.asm \
chkequ.inc chkmacro.inc chkchng.inc \
makefile chkseg.inc chkdata.inc \
$(inc)\dossym.inc $(inc)\sysmsg.inc $(inc)\devsym.inc \
$(inc)\cpmfcb.inc $(inc)\dosmac.inc $(inc)\ioctl.inc \
$(inc)\syscall.inc
chkdsk2.obj: chkdsk2.asm \
chkequ.inc chkmacro.inc chkchng.inc \
makefile chkseg.inc \
$(inc)\dossym.inc $(inc)\sysmsg.inc $(inc)\devsym.inc \
$(inc)\cpmfcb.inc $(inc)\dosmac.inc $(inc)\ioctl.inc \
$(inc)\syscall.inc
chkproc.obj: chkproc.asm \
chkequ.inc chkmacro.inc chkchng.inc \
makefile chkseg.inc \
$(inc)\dossym.inc $(inc)\sysmsg.inc $(inc)\devsym.inc \
$(inc)\cpmfcb.inc $(inc)\dosmac.inc $(inc)\ioctl.inc \
$(inc)\syscall.inc
chkproc2.obj: chkproc2.asm \
chkequ.inc chkmacro.inc chkchng.inc \
makefile chkseg.inc \
$(inc)\dossym.inc $(inc)\sysmsg.inc $(inc)\devsym.inc \
$(inc)\cpmfcb.inc $(inc)\dosmac.inc $(inc)\ioctl.inc \
$(inc)\syscall.inc
chkdisk.obj: chkdisk.asm \
chkequ.inc chkmacro.inc chkchng.inc \
makefile chkseg.inc \
$(inc)\dossym.inc $(inc)\sysmsg.inc $(inc)\devsym.inc \
$(inc)\cpmfcb.inc $(inc)\dosmac.inc $(inc)\ioctl.inc \
$(inc)\syscall.inc
chkfat.obj: chkfat.asm \
chkequ.inc chkmacro.inc chkchng.inc \
makefile chkseg.inc \
$(inc)\dossym.inc $(inc)\sysmsg.inc $(inc)\devsym.inc \
$(inc)\cpmfcb.inc $(inc)\dosmac.inc $(inc)\ioctl.inc \
$(inc)\syscall.inc
chkprmt.obj: chkprmt.asm \
chkequ.inc chkmacro.inc chkchng.inc \
makefile chkseg.inc \
$(inc)\dossym.inc $(inc)\sysmsg.inc $(inc)\devsym.inc \
$(inc)\cpmfcb.inc $(inc)\dosmac.inc $(inc)\ioctl.inc \
$(inc)\syscall.inc
#chkexec.obj: chkexec.asm \ ;an038;bgb #commented out when received from IBM (mrw)
# chkequ.inc chkmacro.inc chkchng.inc \ ;an038;bgb
# makefile chkseg.inc \ ;an038;bgb
# $(inc)\dossym.inc $(inc)\sysmsg.inc $(inc)\devsym.inc \ ;an038;bgb
# $(inc)\cpmfcb.inc $(inc)\dosmac.inc $(inc)\ioctl.inc \ ;an038;bgb
# $(inc)\syscall.inc ;an038;bgb
chkdisp.obj: chkdisp.asm \
chkdsk.ctl \
chkdsk.cla chkdsk.clb chkdsk.clc chkdsk.cld chkdsk.cl1 chkdsk.cl2 \
chkequ.inc chkmacro.inc chkparse.inc chkmsg.inc chkchng.inc \
makefile chkseg.inc \
$(inc)\dossym.inc $(inc)\sysmsg.inc $(inc)\devsym.inc \
$(inc)\cpmfcb.inc $(inc)\dosmac.inc $(inc)\ioctl.inc \
$(inc)\syscall.inc
chkdsk.com: chkdsk1.obj chkdsk2.obj chkproc.obj chkproc2.obj chkprmt.obj \
chkdisk.obj chkfat.obj \
chkinit.obj chkdisp.obj \
chkdsk.lnk makefile
link @chkdsk.lnk
convert chkdsk.exe

View File

@ -0,0 +1,32 @@
;***********************************************************************
; NAME: pathlabl
; DESC: creates a public label at the spot it is placed, using the name
; given.
; INPUT: either module name or procedure name
; OUTPUT: public label
; LOGIC: if masm is in pass1 (pass2 will gen dup labels)
; if this label has not been gen before
; then create the label
; - $$A to place at begin of map
; - start means first occurence
; - use module/proc name last
; define this label for creation of 'stop' label
; else create stop label
; - same as start except name
;***********************************************************************
.LALL
pathlabl MACRO pnam
IF1 ;if pass 1
IFNDEF LBL_&pnam ;switch not defined if first creation
$$A_START_&pnam: ;create label
PUBLIC $$A_START_&pnam ;make it public
LBL_&pnam = 1 ;set switch
ELSE ;start label already created
$$A_STOP_&pnam: ;create stop label
PUBLIC $$A_STOP_&pnam ;make it public
ENDIF
ENDIF
ENDM


View File

@ -0,0 +1,241 @@
; SCCSID = @(#)comequ.asm 1.1 85/05/14
; SCCSID = @(#)comequ.asm 1.1 85/05/14
;*************************************
; COMMAND EQUs which are not switch dependant
EMGDEBUG = FALSE
SYM EQU ">"
LINESPERPAGE EQU 25 ;AC000; default lines per page
NORMPERLIN EQU 1
WIDEPERLIN EQU 5
COMBUFLEN EQU 128 ; Length of commmand buffer
BatLen EQU 32 ; buffer for batch files
YES_ECHO EQU 1 ; echo line
NO_ECHO EQU 0 ; don't echo line
No_Echo_Char EQU "@" ; don't echo line if this is first char
call_in_progress EQU 1 ; indicate we're in the CALL command
length_call EQU 4 ; length of CALL
max_nest EQU 10 ; max # levels of batch nesting allowed
fail_allowed EQU 00001000b ; critical error
retry_allowed EQU 00010000b ; critical error
Ignore_allowed EQU 00100000b ; critical error
nullcommand EQU 1 ; no command on command line
end_of_line EQU -1 ;AN000; end of line return from parser
end_of_line_out EQU 0 ;AN000; end of line for output
end_of_line_in EQU 0dh ;AN000; end of line for input
result_number EQU 1 ;AN000; number returned from parser
result_string EQU 3 ;AN000; string returned from parser
result_filespec EQU 5 ;AN000; filespec returned from parser
result_drive EQU 6 ;AN000; drive returned from parser
result_date EQU 7 ;AN000; date returned from parser
result_time EQU 8 ;AN000; time returned from parser
result_no_error EQU 0 ;AN000; no error returned from parser
no_cont_flag EQU 0 ;AN000; no control flags for message
util_msg_class EQU -1 ;AN000; message class for utility
ext_msg_class EQU 1 ;AN000; message class for extended error
parse_msg_class EQU 2 ;AN000; message class for parse error
crit_msg_class EQU 3 ;AN000; message class for critical error
ext_crlf_class EQU 081h ;AN054; message class for extended error with no CRLF
colon_char EQU ":" ;AN000; colon character
crt_ioctl_ln EQU 14 ;AN000; default length of data for display ioctl
text_mode EQU 1 ;AN000; text mode return from ioctl
get_generic EQU 07Fh ;AN000; generic ioctl - get device info
set_crit_dev EQU 0100H ;AN000; device attribute for critical error on I/0
mult_ansi EQU 01Ah ;AC064; multiplex for ansi.sys
mult_shell_get EQU 01902h ;AC065; multiplex for Shell - get next command
mult_shell_brk EQU 01903h ;AN000; multiplex for Shell - ^C batch check
shell_action equ 0ffh ;AN000; SHELL - return for taking SHELL specific action
bat_not_open EQU -1 ;AN000; batch handle will be set to this if not open
bat_open_handle EQU 19 ;AN000; handle will be in this position in JFN table
Ptr_seg_pos equ 7 ;AN000; Offset from start of message block for subst segment
Ptr_off_pos equ 5 ;AN000; Offset from start of message block for subst offset
Parm_off_pos equ word ptr 2 ;AN000; Offset from start of subst list for subst offset
parm_block_size equ 11 ;AN000; size of message subst block
blank equ " " ;AN000; blank character
no_subst equ 0 ;AN000; no substitutions for messages
one_subst equ 1 ;AN000; one substitution for messages
no_handle_out equ -1 ;AN000; use function 1 thru 12 for message retriever
res_subst equ 2 ;AN000; offset from start of message definition to number of subst
read_open_mode equ 0000000000000000b ;AN024; extended open mode for read
read_open_flag equ 0000000100000001b ;AN000; extended open flags for read
write_open_mode equ 0000000000000001b ;AN024; extended open mode for read
write_open_flag equ 0000000100000001b ;AN000; extended open flags for read
creat_open_flag equ 0000000100010010b ;AN000; extended open flags for read
get_CPSW equ 3 ;AN000; minor function for get CPSW status
CPSW_off equ 0 ;AN000; CPSW return from function - OFF
Get_XA equ 2 ;AN030; minor function for get extended attributes
Set_XA equ 4 ;AN000; minor function for set extended attributes
file_no_cpage equ 0 ;AN000; file has no code page tag
file_inv_cpage equ -1 ;AN000; file has invalid code page tag
do_xa equ -1 ;AN000; flag to get extended attributes
inv_cp_tag equ 0 ;AC039; tag for invalid code page
no_xa_seg equ -1 ;AN000; no segment for extended attributes - COPY
capital_A equ 'A' ;AC000;
vbar equ '|' ;AC000;
labracket equ '<' ;AC000;
rabracket equ '>' ;AC000;
dollar equ '$' ;AC000;
lparen equ '(' ;AC000;
rparen equ ')' ;AC000;
nullrparen equ 29h ;AC000;
in_word equ 4e49h ;AC000; 'NI' ('IN' backwards)
do_word equ 4f44h ;AC000; 'OD' ('DO' backwards)
star equ '*' ;AC000;
plus_chr equ '+' ;AC000;
small_a equ 'a' ;AC000;
small_z equ 'z' ;AC000;
dot_chr equ '.' ;AC000;
tab_chr equ 9 ;AN032;
equal_chr equ '=' ;AN032;
semicolon equ ';' ;AN049;
dot_qmark equ 2e3fh ;AC000; '.?'
dot_colon equ 2e3ah ;AC000; '.:'
capital_n equ 0 ;AC000; result from Y/N call if N entered
capital_y equ 1 ;AC000; result from Y/N call if Y entered
AppendInstall equ 0B700H ;AN020; append install check
AppendDOS equ 0B702H ;AN020; append DOS version check
AppendGetState equ 0B706H ;AN020; append get current state
AppendSetState equ 0B707H ;AN020; append set current state
AppendTruename equ 0B711H ;AN042; Get file's real location for Batch
search_attr equ attr_read_only+attr_hidden+attr_directory ;AC042;
;*************************************
;* PARSE ERROR MESSAGES
;*************************************
MoreArgs_Ptr equ 1 ;AN000;"Too many parameters" message number
LessArgs_Ptr equ 2 ;AN000;"Required parameter missing" message number
BadSwt_Ptr equ 3 ;AN000;"Invalid switch" message number
BadParm_Ptr equ 10 ;AN000;"Invalid parameter" message number
;*************************************
;* EQUATES FOR MESSAGE RETRIEVER
;*************************************
GET_EXTENDED_MSG EQU 0 ;AN000; get extended message address
SET_EXTENDED_MSG EQU 1 ;AN000; set extended message address
GET_PARSE_MSG EQU 2 ;AN000; get parse message address
SET_PARSE_MSG EQU 3 ;AN000; set parse message address
GET_CRITICAL_MSG EQU 4 ;AN000; get critical message address
SET_CRITICAL_MSG EQU 5 ;AN000; set critical message address
MESSAGE_2F EQU 46 ;AN000; minor code for message retriever
;*********************************
;* EQUATES FOR INT 10H
;*********************************
VIDEO_IO_INT EQU 10H ;AN000; equate for int 10h
SET_VIDEO_MODE EQU 0 ;AN000; set video mode
SET_CURSOR_POSITION EQU 2 ;AN000; set new cursor position
SCROLL_VIDEO_PAGE EQU 6 ;AN000; scroll active page up
VIDEO_ATTRIBUTE EQU 7 ;AN000; attribute to be used on blank line
SET_COLOR_PALETTE EQU 11 ;AN000; set color for video
GET_VIDEO_STATE EQU 15 ;AN000; get current video state
VIDEO_ALPHA EQU 3 ;AN000; alpha video is 3 or below
VIDEO_BW EQU 7 ;AN000; mode for 80X25 black & white
AltPipeChr equ "|" ; alternate pipe character
FCB EQU 5CH
VARSTRUC STRUC
ISDIR DB ?
SIZ DB ?
TTAIL DW ?
INFO DB ?
BUF DB DIRSTRLEN + 20 DUP (?)
VARSTRUC ENDS
fCheckDrive equ 00000001b
fSwitchAllowed equ 00000010b
;
; Test switches
;
fParse EQU 0001h ; display results of parseline
;
; Batch segment structure
;
; BYTE type of segment
; BYTE echo state of parent on entry to batch file
; WORD segment of last batch file
; WORD segment for FOR command
; BYTE FOR flag state on entry to batch file
; DWORD offset for next line
; 10 WORD pointers to parameters. -1 is empty parameter
; ASCIZ file name (with . and ..)
; BYTES CR-terminated parameters
; BYTE 0 flag to indicate end of parameters
;
BatchType equ 0
BatchSegment struc
BatType DB BatchType ; signature
Batechoflag DB 0 ; G state of echo
Batlast DW 0 ; G segment of last batch file
Batforptr DW 0 ; G segment for FOR command
Batforflag DB 0 ; G state of FOR
BatSeek DD ? ; lseek position of next char
BatParm DW 10 dup (?) ; pointers to parameters
BatFile DB ? ; beginning of batch file name
BatchSegment ends
ANULL equ 0 ; terminates an argv string
ARGMAX equ 64 ; max args on a command line
ARGBLEN equ 2*128 ; 1char each plus term NUL
tplen equ 64 ; max size of one argument
arg_cnt_error equ 1 ; number of args > MAXARG
arg_buf_ovflow equ 2 ; overflowed argbuffer
argv_ele STRUC ; elements in the argv array
argpointer DW (?) ; pointer to the argstring
argflags DB (?) ; cparse flags for this argstring
argstartel DW (?) ; the result of cparse's [STARTEL]
arglen DW (?) ; cparse's char count + one (for null)
argsw_word DW (?) ; any switches after this? what kinds?
arg_ocomptr DW (?) ; pointer into original command string
argv_ele ENDS
arg_unit STRUC
argv DB (ARGMAX * SIZE argv_ele) DUP (?)
argvcnt DW (?) ; number of arguments
argswinfo DW (?) ; Switch information for entire line
argbuf DW ARGBLEN DUP (?) ; storage for argv strings
argforcombuf db COMBUFLEN DUP (?) ; Original for loop command string
arg_unit ENDS
parseflags RECORD special_delim:1, unused:4, path_sep:1, wildcard:1, sw_flag:1
SwitchV EQU 10h
SwitchB EQU 08h
SwitchA EQU 04h
SwitchP EQU 02h
SwitchW EQU 01h
fSwitch EQU 8000h
fBadSwitch EQU 4000h
SwitchDir EQU SwitchP + SwitchW + fSwitch
SwitchCopy EQU SwitchV + SwitchA + SwitchB + fSwitch
break <Trap: Get the attention of MSDOS>
; TRAP snares the operating system for a service call
; AX, as well as any other registers MS-DOS takes a fancy to, will be crunched.
trap MACRO dos_function,dos_info
ifnb <dos_info>
mov AX, (dos_function SHL 8) + dos_info
else
mov AX, (dos_function SHL 8)
endif
int int_command
ENDM
;
; Equates for initialization
;
initInit equ 01h ; initialization in progress
initSpecial equ 02h ; in initialization time/date routine
initCtrlC equ 04h ; already in ^C handler

View File

@ -0,0 +1,6 @@
/map COMMAND1.OBJ COMMAND2.OBJ RUCODE.OBJ RDATA.OBJ INIT.OBJ IPARSE.OBJ +
UINIT.OBJ TCODE.OBJ TBATCH.OBJ TBATCH2.OBJ TFOR.OBJ TCMD1A.OBJ TCMD1B.OBJ +
TCMD2A.OBJ TCMD2B.OBJ TENV.OBJ TENV2.OBJ TMISC1.OBJ TMISC2.OBJ TPIPE.OBJ +
PARSE2.OBJ PATH1.OBJ PATH2.OBJ TUCODE.OBJ COPY.OBJ COPYPR1.OBJ COPYPR2.OBJ +
CPARSE.OBJ TPARSE.OBJ TPRINTF.OBJ TDATA.OBJ TSPC.OBJ,COMMAND.EXE,,;


View File

@ -0,0 +1,213 @@
;*************************
;* MESSAGE SKELETON FILE *
;*************************
:util COMMAND ;AC000;
:class 1 ;AC000; Transient extended errors
:use EXTEND2 ;AC000; "File not found"
:use EXTEND3 ;AC000; "Path not found"
:use EXTEND8 ;AC000; "Insufficient memory"
:class 2 ;AC000; Transient parse errors
:class 3 ;AC000; Resident extended errors
:use -1 EXTEND999 ;AN000; "Extended error #"
:class 4 ;AC000; Resident parse errors
:use -1 PARSE999 ;AN000; "Parse error #"
:class A ;AC000; resident messages
:use 220 COMMON17 ;AC000; "File allocation table bad, drive %1"
:use 223 COMMON28 ;AC000; "Press any key to continue"
:def 201 "A" ;AC000;
:def 202 "R" ;AC000;
:def 203 "I" ;AC000;
:def 204 "F" ;AC000;
:def 205 "Y" ;AC000;
:def 206 "N" ;AC000;
:def 210 "Abort" ;AC000;
:def 211 ", Retry" ;AC000;
:def 212 ", Ignore" ;AC000;
:def 213 ", Fail" ;AC000;
:def 214 "?" ;AC000;
:def 215 "reading",0 ;AC000;
:def 216 "writing",0 ;AC000;
:def 217 " %1 drive %2",CR,LF ;AC000;
:def 218 " %1 device %2",CR,LF ;AC000;
:def 219 "Please insert volume %1 serial %2-%3",CR,LF ;AC009;
:def 221 "Invalid COMMAND.COM",CR,LF ;AC000;
:def 222 "Insert disk with %1 in drive %2",CR,LF ;AC000;
:def 224 CR,LF,"Terminate batch job (Y/N)?" ;AC000;
:def 225 "Cannot execute %1",CR,LF ;AC000;
:def 226 "Error in EXE file",CR,LF ;AC000;
:def 227 "Program too big to fit in memory",CR,LF ;AC000;
:def 228 CR,LF,"No free file handles" ;AC000;
:def 229 "Bad Command or file name",CR,LF ;AC000;
:use 230 EXTEND5 ;AC000;
:def 231 CR,LF,"Memory allocation error" ;AC000;
:def 232 CR,LF,"Cannot load COMMAND, system halted",CR,LF;AC000;
:def 233 CR,LF,"Cannot start COMMAND, exiting",CR,LF ;AC000;
:def 234 CR,LF,"Top level process aborted, cannot continue",CR,LF;AC000;
:def 235 CR,LF ;AC000;
:class B ;AC000; Initialization messages
:use 461 COMMON1 ;AC000; "Incorrect DOS version"
:def 463 "Out of environment space",CR,LF ;AC000;
:def 464 CR,LF,CR,LF,"MS DOS ",CR,LF
"Version 4.00 (C)Copyright International Business Machines Corp 1981,1988",CR,LF
" (C)Copyright Microsoft Corp 1981, 1988",CR,LF ;AC000;
:def 465 "Specified COMMAND search directory bad",CR,LF ;AC025;
:def 466 "Specified COMMAND search directory bad access denied",CR,LF ;AC025;
:class C ;AC000; Parse messages
:use PARSE1 ;AC000; "Too many parameters"
:use PARSE2 ;AC000; "Required parameter missing"
:use PARSE3 ;AC000; "Invalid switch"
:use PARSE4 ;AC000; "Invalid keyword"
:use PARSE6 ;AC000; "Parameter value not in allowed range"
:use PARSE7 ;AC000; "Parameter value not allowed"
:use PARSE8 ;AC000; "Parameter value not allowed"
:use PARSE9 ;AC000; "Parameter format not correct"
:use PARSE10 ;AC000; "Invalid parameter"
:use PARSE11 ;AC000; "Invalid parameter combination"
:class D ;AC000; Extended errors - critical
:use EXTEND19 ;AC000; "Write protect"
:use EXTEND20 ;AC000; "Invalid unit"
:use EXTEND21 ;AC000; "Drive not ready"
:use EXTEND22 ;AC000; "Invalid device request"
:use EXTEND23 ;AC000; "Data error"
:use EXTEND24 ;AC000; "Invalid device request parameters"
:use EXTEND25 ;AC000; "Seek error"
:use EXTEND26 ;AC000; "Invalid media type"
:use EXTEND27 ;AC000; "Sector not found"
:use EXTEND28 ;AC000; "Printer out of paper"
:use EXTEND29 ;AC000; "Write fault error"
:use EXTEND30 ;AC000; "Read fault error"
:use EXTEND31 ;AC000; "General Failure"
:use EXTEND32 ;AC000; "Sharing Violation"
:use EXTEND33 ;AC000; "Lock Violation"
:use EXTEND34 ;AC000; "Invalid Disk Change"
:use EXTEND35 ;AC000; "FCB unavailable"
:use EXTEND36 ;AC000; "System resource exhausted"
:use EXTEND37 ;AC000; "Code page mismatch"
:use EXTEND38 ;AC026; "Out of input"
:use EXTEND39 ;AC026; "Insufficient disk space"
:class E ;AC000; extended errors
:use EXTEND1 ;AC000; "Invalid Function"
:use EXTEND2 ;AC000; "File not found"
:use EXTEND3 ;AC000; "Path not found"
:use EXTEND4 ;AC000; "Too many open files"
:use EXTEND5 ;AC000; "Access denied"
:use EXTEND6 ;AC000; "Invalid handle"
:use EXTEND7 ;AC000; "Memory control blocks destroyed"
:use EXTEND8 ;AC000; "Insufficient memory"
:use EXTEND9 ;AC000; "Invalid memory block address"
:use EXTEND10 ;AC000; "Invalid Environment"
:use EXTEND11 ;AC000; "Invalid format"
:use EXTEND12 ;AC000; "Invalid function parameter"
:use EXTEND13 ;AC000; "Invalid data"
:use EXTEND15 ;AC000; "Invalid drive specification"
:use EXTEND16 ;AC000; "Attempt to remove current directory"
:use EXTEND17 ;AC000; "Not same device"
:use EXTEND18 ;AC000; "No more files"
:use EXTEND80 ;AC000; "File already exists"
:use EXTEND82 ;AC000; "Can not make directory entry"
:use EXTEND83 ;AC000; "Fail requested to Critical Error"
:use EXTEND84 ;AC000; "Too many attaches"
:use EXTEND85 ;AC000; "Device or file already attached"
:use EXTEND86 ;AC000; "Invalid password"
:use EXTEND87 ;AC000; "Invalid parameter"
:use EXTEND88 ;AC000; "File system data fault"
:use EXTEND89 ;AC000; "Function not supported by file system"
:use EXTEND90 ;AC000;
:class F ;AC000; Transient messages
:use 1020 COMMON4 ;AC000; "%1 bytes free",CR,LF
:use 1015 COMMON18 ;AC000; "File cannot be copied onto itself",CR,LF
:use 1004 COMMON20 ;AC000; "Insufficient disk space",CR,LF
:use 1026 COMMON22 ;AC000; "Invalid code page",CR,LF
:use 1031 COMMON23 ;AC000; "Invalid date"
:use 1035 COMMON24 ;AC000; "Invalid time"
:use 1062 COMMON25 ;AC000; "Invalid path"
:use 1028 COMMON28 ;AC000; "Press any key to continue"
:use 1045 COMMON32 ;AC000; "Unable to create directory",CR,LF
:use 1041 COMMON33 ;AC000; "Volume in drive %1 has no label"
:use 1042 COMMON34 ;AC000; "Volume in drive %1 is %2"
:use 1043 COMMON36 ;AC000; "Volume Serial Number is %1"
:def 1002 "Duplicate file name or file not found",CR,LF ;AC000;
:def 1003 "Invalid path or file name",CR,LF ;AC000;
:def 1007 "Out of environment space",CR,LF ;AC000;
:def 1008 "File creation error",CR,LF ;AC000;
:def 1009 "Batch file missing",CR,LF ;AC000;
:def 1010 CR,LF,"Insert disk with batch file",CR,LF ;AC000;
:def 1011 "Bad command or file name",CR,LF ;AC000;
:use 1014 EXTEND5 ;AC000;
:def 1016 "Content of destination lost before copy",CR,LF ;AC000;
:def 1017 "Invalid filename or file not found",CR,LF ;AC000;
:def 1018 "%1 File(s) copied",CR,LF ;AC000;
:def 1019 "%1 File(s) " ;AC000;
:use 1021 EXTEND15 ;AC000;
:def 1022 "Code page %1 not prepared for system",CR,LF ;AC000;
:def 1023 "Code page %1 not prepared for all devices",CR,LF ;AC000;
:def 1024 "Active code page: %1",CR,LF ;AC000;
:def 1025 "NLSFUNC not installed",CR,LF ;AC000;
:def 1027 "Current drive is no longer valid" ;AC000;
:def 1029 "Label not found",CR,LF ;AC000;
:def 1030 "Syntax error",CR,LF ;AC000;
:def 1032 "Current date is %1 %2",CR,LF ;AC000;
:def 1033 "SunMonTueWedThuFriSat" ;AC000;
:def 1034 "Enter new date (%1): " ;AC031;
:def 1036 "Current time is %1",CR,LF ;AC000;
:def 1037 "Enter new time: " ;AC031;
:def 1038 ", Delete (Y/N)?" ;AC000;
:def 1039 "All files in directory will be deleted!",CR,LF
"Are you sure (Y/N)?" ;AC000;
:def 1040 "Microsoft DOS Version %1.%2",CR,LF ;AC000;
:def 1044 "Invalid directory",CR,LF ;AC000;
:def 1046 "Invalid path, not directory,",CR,LF,"or directory not empty",CR,LF ;AC000;
:def 1047 "Must specify ON or OFF",CR,LF ;AC000;
:def 1048 "Directory of %1",CR,LF ;AC000;
:def 1049 "No Path",CR,LF ;AC000;
:def 1050 "Invalid drive in search path",CR,LF ;AC000;
:def 1051 "Invalid device",CR,LF ;AC000;
:def 1052 "FOR cannot be nested",CR,LF ;AC000;
:def 1053 "Intermediate file error during pipe",CR,LF ;AC000;
:def 1054 "Cannot do binary reads from a device",CR,LF ;AC000;
:def 1055 "BREAK is %1",CR,LF ;AC000;
:def 1056 "VERIFY is %1",CR,LF ;AC000;
:def 1057 "ECHO is %1",CR,LF ;AC000;
:def 1059 "off",0 ;AC000;
:def 1060 "on",0 ;AC000;
:def 1061 "Error writing to device",CR,LF ;AC000;
:def 1063 "%1" ;AC000;
:def 1064 "%1" ;AC000;
:def 1065 "%1" ;AC000;
:def 1066 "%1" ;AC000;
:def 1067 9 ;AC000;
:def 1068 " <DIR> " ;AC000;
:def 1069 8," ",8 ;AC000;
:def 1070 CR,LF ;AC000;
:def 1071 "%1" ;AC000;
:def 1072 "mm-dd-yy" ;AC000;
:def 1073 "dd-mm-yy" ;AC000;
:def 1074 "yy-mm-dd" ;AC000;
:def 1075 "%1 %2" ;AC000;
:def 1076 "%1" ;AC000;
:def 1077 " %1 %2" ;AC053;
:def 1078 "Directory already exists",CR,LF ;AC000;
:end ;AC000;

View File

@ -0,0 +1,638 @@
page 80,132
; SCCSID = @(#)command1.asm 1.1 85/05/14
; SCCSID = @(#)command1.asm 1.1 85/05/14
TITLE COMMAND - resident code for COMMAND.COM
NAME COMMAND
;*****************************************************************************
;
; MODULE: COMMAND.COM
;
; DESCRIPTIVE NAME: Default DOS command interpreter
;
; FUNCTION: This version of COMMAND is divided into three distinct
; parts. First is the resident portion, which includes
; handlers for interrupts 23H (Cntrl-C), 24H (fatal
; error), and 2EH (command line execute); it also has
; code to test and, if necessary, reload the transient
; portion. Following the resident is the init code, which
; is overwritten after use. Then comes the transient
; portion, which includes all command processing (whether
; internal or external). The transient portion loads at
; the end of physical memory, and it may be overlayed by
; programs that need as much memory as possible. When the
; resident portion of command regains control from a user
; program, a check sum is performed on the transient
; portion to see if it must be reloaded. Thus programs
; which do not need maximum memory will save the time
; required to reload COMMAND when they terminate.
;
; ENTRY POINT: PROGSTART
;
; INPUT: command line at offset 81H
;
; EXIT_NORMAL: No exit from root level command processor. Can exit
; from a secondary command processor via the EXIT
; internal command.
;
; EXIT_ERROR: Exit to prior command processor if possible, otherwise
; hang the system.
;
; INTERNAL REFERENCES:
;
; ROUTINES: See the COMMAND Subroutine Description Document
; (COMMAND.DOC)
;
; DATA AREAS: See the COMMAND Subroutine Description Document
; (COMMAND.DOC)
;
; EXTERNAL REFERENCES:
;
; ROUTINES: none
;
; DATA AREAS: none
;
;*****************************************************************************
;
; REVISION HISTORY
; ----------------
;
; DOS 1.00 to DOS 3.30
; --------------------------
; SEE REVISION LOG IN COPY.ASM ALSO
;
; REV 1.17
; 05/19/82 Fixed bug in BADEXE error (relocation error must return to
; resident since the EXELOAD may have overwritten the transient.
;
; REV 1.18
; 05/21/82 IBM version always looks on drive A
; MSVER always looks on default drive
;
; REV 1.19
; 06/03/82 Drive spec now entered in command line
; 06/07/82 Added VER command (print DOS version number) and VOL command
; (print volume label)
;
; REV 1.20
; 06/09/82 Prints "directory" after directories
; 06/13/82 MKDIR, CHDIR, PWD, RMDIR added
;
; REV 1.50
; Some code for new 2.0 DOS, sort of HACKey. Not enough time to
; do it right.
;
; REV 1.70
; EXEC used to fork off new processes
;
; REV 1.80
; C switch for single command execution
;
; REV 1.90
; Batch uses XENIX
;
; Rev 2.00
; Lots of neato stuff
; IBM 2.00 level
;
; Rev 2.01
; 'D' switch for date time suppression
;
; Rev 2.02
; Default userpath is NUL rather than BIN
; same as IBM
; COMMAND split into pieces
;
; Rev 2.10
; INTERNATIONAL SUPPORT
;
; Rev 2.50
; all the 2.x new stuff -MU
;
; Rev 3.30 (Ellen G)
; CALL internal command (TBATCH2.ASM)
; CHCP internal command (TCMD2B.ASM)
; INT 24H support of abort, retry, ignore, and fail prompt
; @ sign suppression of batch file line
; Replaceable environment value support in batch files
; INT 2FH calls for APPEND
; Lots of PTR fixes!
;
; Beyond 3.30 to forever (Ellen G)
; ----------------------
;
; A000 DOS 4.00 - Use SYSPARSE for internal commands
; Use Message Retriever services
; /MSG switch for resident extended error msg
; Convert to new capitalization support
; Better error recovery on CHCP command
; Code page file tag support
; TRUENAME internal command
; Extended screen line support
; /P switch on DEL/ERASE command
; Improved file redirection error recovery
; (removed) Improved batch file performance
; Unconditional DBCS support
; Volume serial number support
; (removed) COMMENT=?? support
;
; A001 PTM P20 Move system_cpage from TDATA to TSPC
;
; A002 PTM P74 Fix PRESCAN so that redirection symbols do not
; require delimiters.
;
; A003 PTM P5,P9,P111 Included in A000 development
;
; A004 PTM P86 Fix IF command to turn off piping before
; executing
;
; A005 DCR D17 If user specifies an extension on the command
; line search for that extension only.
;
; A006 DCR D15 New message for MkDir - "Directory already
; exists"
;
; A007 DCR D2 Change CTTY so that a write is done before XDUP
;
; A008 PTM P182 Change COPY to set default if invalid function
; returned from code page call.
;
; A009 PTM P179 Add CRLF to invalid disk change message
;
; A010 DCR D43 Allow APPEND to do a far call to SYSPARSE in
; transient COMMAND.
;
; A011 DCR D130 Change redirection to overwrite an EOF mark
; before appending to a file.
;
; A012 PTM P189 Fix redirection error recovery.
;
; A013 PTM P330 Change date format
;
; A014 PTM P455 Fix echo parsing
;
; A015 PTM P517 Fix DIR problem with * vs *.
;
; A016 PTM P354 Fix extended error message addressing
;
; A017 PTM P448 Fix appending to 0 length files
;
; A018 PTM P566,P3903 Fix parse error messages to print out parameter
; the parser fails on. Fail on duplicate switches.
;
; A019 PTM P542 Fix device name to be printed correctly during
; critical error
;
; A020 DCR D43 Set append state off while in DIR
;
; A021 PTM P709 Fix CTTY printing ascii characters.
;
; A022 DCR D209 Enhanced error recovery
;
; A023 PTM P911 Fix ANSI.SYS IOCTL structure.
;
; A024 PTM P899 Fix EXTOPEN open modes.
;
; A025 PTM P922 Fix messages and optimize PARSE switches
;
; A026 DCR D191 Change redirection error recovery support.
;
; A027 PTM P991 Fix so that KAUTOBAT & AUTOEXEC are terminated
; with a carriage return.
;
; A028 PTM P1076 Print a blank line before printing invalid
; date and invalid time messages.
;
; A029 PTM P1084 Eliminate calls to parse_check_eol in DATE
; and TIME.
;
; A030 DCR D201 New extended attribute format.
;
; A031 PTM P1149 Fix DATE/TIME add blank before prompt.
;
; A032 PTM P931 Fix =ON, =OFF for BREAK, VERIFY, ECHO
;
; A033 PTM P1298 Fix problem with system crashes on ECHO >""
;
; A034 PTM P1387 Fix COPY D:fname+,, to work
;
; A035 PTM P1407 Fix so that >> (appending) to a device does
; do a read to determine eof.
;
; A036 PTM P1406 Use 69h instead of 44h to get volume serial
; so that ASSIGN works correctly.
;
; A037 PTM P1335 Fix COMMAND /C with FOR
;
; A038 PTM P1635 Fix COPY so that it doesn't accept /V /V
;
; A039 DCR D284 Change invalid code page tag from -1 to 0.
;
; A040 PTM P1787 Fix redirection to cause error when no file is
; specified.
;
; A041 PTM P1705 Close redirected files after internal APPEND
; executes.
;
; A042 PTM P1276 Fix problem of APPEND paths changes in batch
; files causing loss of batch file.
;
; A043 PTM P2208 Make sure redirection is not set up twice for
; CALL'ed batch files.
;
; A044 PTM P2315 Set switch on PARSE so that 0ah is not used
; as an end of line character
;
; A045 PTM P2560 Make sure we don't lose parse, critical error,
; and extended message pointers when we EXIT if
; COMMAND /P is the top level process.
;
; A046 PTM P2690 Change COPY message "fn File not found" to
; "File not found - fn"
;
; A047 PTM P2819 Fix transient reload prompt message
;
; A048 PTM P2824 Fix COPY path to be upper cased. This was broken
; when DBCS code was added.
;
; A049 PTM P2891 Fix PATH so that it doesn't accept extra characters
; on line.
;
; A050 PTM P3030 Fix TYPE to work properly on files > 64K
;
; A051 PTM P3011 Fix DIR header to be compatible with prior releases.
;
; A052 PTM P3063,P3228 Fix COPY message for invalid filename on target.
;
; A053 PTM P2865 Fix DIR to work in 40 column mode.
;
; A054 PTM P3407 Code reduction and critical error on single line
; PTM P3672 (Change to single parser exported under P3407)
;
; A055 PTM P3282 Reset message service variables in INT 23h to fix
; problems with breaking out of INT 24h
;
; A056 PTM P3389 Fix problem of environment overlaying transient.
;
; A057 PTM P3384 Fix COMMAND /C so that it works if there is no space
; before the "string". EX: COMMAND /CDIR
;
; A058 PTM P3493 Fix DBCS so that CPARSE eats second character of
; DBCS switch.
;
; A059 PTM P3394 Change the TIME command to right align the display of
; the time.
;
; A060 PTM P3672 Code reduction - change PARSE and EXTENDED ERROR
; messages to be disk based. Only keep them if /MSG
; is used.
;
; A061 PTM P3928 Fix so that transient doesn't reload when breaking
; out of internal commands, due to substitution blocks
; not being reset.
;
; A062 PTM P4079 Fix segment override for fetching address of environment
; of parent copy of COMMAND when no COMSPEC exists in
; secondary copy of environment. Change default slash in
; default comspec string to backslash.
; A063 PTM P4140 REDIRECTOR and IFSFUNC changed interface for getting
; text for critical error messages.
; A064 PTM P4934 Multiplex number for ANSI.SYS changed due to conflict
; 5/20/88 with Microsoft product already shipped.
; A065 PTM P4935 Multiplex number for SHELL changed due to conflict with
; 5/20/88 with Microsoft product already shipped.
; A066 PTM P4961 DIR /W /P scrolled first line off the screen in some
; 5/24/88 cases; where the listing would barely fit without the
; header and space remaining.
; A067 PTM P5011 For /E: values of 993 to 1024 the COMSPEC was getting
; 6/6/88 trashed. Turns out that the SETBLOCK for the new
; environment was putting a "Z block" marker in the old
; environment. The fix is to move to the old environment
; to the new environment before doing the SETBLOCK.
;***********************************************************************************
.XCREF
.XLIST
INCLUDE DOSSYM.INC
INCLUDE comsw.asm
INCLUDE comequ.asm
INCLUDE resmsg.equ ;AN000;
.LIST
.CREF
CODERES SEGMENT PUBLIC BYTE ;AC000;
CODERES ENDS
DATARES SEGMENT PUBLIC BYTE
EXTRN BATCH:WORD
EXTRN ECHOFLAG:BYTE
EXTRN disp_class:byte ;AN055;
EXTRN execemes_block:byte ;AC000;
EXTRN execemes_off:word ;AC000;
EXTRN execemes_subst:byte ;AC000;
EXTRN execemes_seg:word ;AC000;
EXTRN EXTCOM:BYTE
EXTRN FORFLAG:BYTE
EXTRN IFFlag:BYTE
EXTRN InitFlag:BYTE
EXTRN NEST:WORD
EXTRN number_subst:byte ;AC000;
EXTRN PIPEFLAG:BYTE
EXTRN RETCODE:WORD
EXTRN SINGLECOM:WORD
DATARES ENDS
BATARENA SEGMENT PUBLIC PARA ;AC000;
BATARENA ENDS
BATSEG SEGMENT PUBLIC PARA ;AC000;
BATSEG ENDS
ENVARENA SEGMENT PUBLIC PARA ;AC000;
ENVARENA ENDS
ENVIRONMENT SEGMENT PUBLIC PARA ; Default COMMAND environment
ENVIRONMENT ENDS
INIT SEGMENT PUBLIC PARA
EXTRN CONPROC:NEAR
EXTRN init_contc_specialcase:near
INIT ENDS
TAIL SEGMENT PUBLIC PARA
TAIL ENDS
TRANCODE SEGMENT PUBLIC PARA
TRANCODE ENDS
TRANDATA SEGMENT PUBLIC BYTE
TRANDATA ENDS
TRANSPACE SEGMENT PUBLIC BYTE
TRANSPACE ENDS
TRANTAIL SEGMENT PUBLIC PARA
TRANTAIL ENDS
RESGROUP GROUP CODERES,DATARES,BATARENA,BATSEG,ENVARENA,ENVIRONMENT,INIT,TAIL
TRANGROUP GROUP TRANCODE,TRANDATA,TRANSPACE,TRANTAIL
INCLUDE envdata.asm
; START OF RESIDENT PORTION
CODERES SEGMENT PUBLIC BYTE ;AC000;
PUBLIC EXT_EXEC
PUBLIC CONTC
PUBLIC Exec_Wait
ASSUME CS:RESGROUP,DS:NOTHING,ES:NOTHING,SS:NOTHING
EXTRN lodcom:near
EXTRN LODCOM1:near
ORG 0
ZERO = $
ORG 80h-1
PUBLIC RESCOM
RESCOM LABEL BYTE
ORG 100H
PROGSTART:
JMP RESGROUP:CONPROC
;
; COMMAND has issued an EXEC system call and it has returned an error. We
; examine the error code and select an appropriate message.
;
EXEC_ERR:
push ds ;AC000; get transient segment
pop es ;AC000; into ES
push cs ;AC000; get resident segment
pop ds ;AC000; into DS
ASSUME DS:RESGROUP ;AN000;
MOV BX,RBADNAM ;AC000; Get message number for Bad command
CMP AX,error_file_not_found
JZ GOTEXECEMES
MOV BX,TOOBIG ;AC000; Get message number for file not found
CMP AX,error_not_enough_memory
JZ GOTEXECEMES
MOV BX,EXEBAD ;AC000; Get message number for bad exe file
CMP AX,error_bad_format
JZ GOTEXECEMES
MOV BX,AccDen ;AC000; Get message number for access denied
CMP AX,error_access_denied
JZ GOTEXECEMES ;AC000; go print message
DEFAULT_MESSAGE:
MOV BX,EXECEMES ;AC000; Get message number for default message
MOV EXECEMES_OFF,DX ;AN000; put offset of EXEC string in subst block
MOV EXECEMES_SEG,ES ;AN000; put segment of EXEC string in subst block
MOV AL,EXECEMES_SUBST ;AN000; get number of substitutions
MOV NUMBER_SUBST,AL ;AN000;
MOV SI,OFFSET RESGROUP:EXECEMES_BLOCK ;AN000; get address of subst block
GOTEXECEMES:
PUSH CS
POP ES ;AC000; get resident segment into ES
ASSUME ES:RESGROUP ;AN000;
MOV DX,BX ;AN000; get message number in DX
INVOKE RPRINT
JMP SHORT NOEXEC
;
; The transient has set up everything for an EXEC system call. For
; cleanliness, we issue the EXEC here in the resident so that we may be able
; to recover cleanly upon success.
;
EXT_EXEC:
push dx ;AN000; save the command name offset
INT int_command ; Do the EXEC
pop dx ;AN000; restore the command name offset
JC EXEC_ERR ; EXEC failed
;
; The exec has completed. Retrieve the exit code.
;
EXEC_WAIT:
push cs ;AC000; get resident segment
pop ds ;AC000; into DS
MOV AH,WAITPROCESS ;AC000; Get errorlevel
INT int_command ; Get the return code
MOV [RETCODE],AX
;
; We need to test to see if we can reload the transient. THe external command
; may have overwritten part of the transient.
;
NOEXEC:
JMP LODCOM
;
; This is the default system INT 23 handler. All processes (including
; COMMAND) get it by default. There are some games that are played: We
; ignore ^C during most of the INIT code. This is because we may perform an
; ALLOC and diddle the header! Also, if we are prompting for date/time in the
; init code, we are to treat ^C as empty responses.
;
CONTC PROC FAR
ASSUME CS:ResGroup,DS:NOTHING,ES:NOTHING,SS:NOTHING
test InitFlag,initINIT ; in initialization?
jz NotAtInit ; no
test InitFlag,initSpecial ; doing special stuff?
jz CmdIRet ; no, ignore ^C
jmp resgroup:init_contc_specialcase ; Yes, go handle it
CmdIret:
iret ; yes, ignore the ^C
NotAtInit:
test InitFlag,initCtrlC ; are we already in a ^C?
jz NotInit ; nope too.
;
; We are interrupting ourselves in this ^C handler. We need to set carry
; and return to the user sans flags only if the system call was a 1-12 one.
; Otherwise, we ignore the ^C.
;
cmp ah,1
jb CmdIRet
cmp ah,12
ja CmdIRet
add sp,6 ; remove int frame
stc
ret 2 ; remove those flags...
;
; We have now received a ^C for some process (maybe ourselves but not at INIT).
;
; Note that we are running on the user's stack!!! Bad news if any of the
; system calls below go and issue another INT 24... Massive stack overflow!
; Another bad point is that SavHand will save an already saved handle, thus
; losing a possible redirection...
;
; All we need to do is set the flag to indicate nested ^C. The above code
; will correctly flag the ^C diring the message output and prompting while
; ignoring the ^C the rest of the time.
;
; Clean up: flush disk. If we are in the middle of a batch file, we ask if
; he wants to terminate it. If he does, then we turn off all internal flags
; and let the DOS abort.
;
NotInit:
or InitFlag,initCtrlC ; nested ^c is on
STI
PUSH CS ; El Yucko! Change the user's DS!!
POP DS
ASSUME DS:RESGROUP
MOV DISP_CLASS,UTIL_MSG_CLASS ;AN055; reset display class
MOV NUMBER_SUBST,NO_SUBST ;AN055; reset number of substitutions
MOV AX,SingleCom
OR AX,AX
JNZ NoReset
PUSH AX
MOV AH,DISK_RESET
INT int_command ; Reset disks in case files were open
POP AX
NoReset:
;
; In the generalized version of FOR, PIPE and BATCH, we would walk the entire
; active list and free each segment. Here, we just free the single batch
; segment.
;
TEST Batch,-1
JZ CONTCTERM
OR AX,AX
JNZ Contcterm
invoke SavHand
invoke ASKEND ; See if user wants to terminate batch
;
; If the carry flag is clear, we do NOT free up the batch file
;
JNC ContBatch
mov cl,echoflag ;AN000; get current echo flag
PUSH BX ;G
ClearBatch:
MOV ES,[BATCH] ; get batch segment
mov di,batfile ;AN000; get offset of batch file name
mov ax,mult_shell_brk ;AN000; does the SHELL want this terminated?
int 2fh ;AN000; call the SHELL
cmp al,shell_action ;AN000; does shell want this batch?
jz shell_bat_cont ;AN000; yes - keep it
MOV BX,ES:[BATFORPTR] ;G get old FOR segment
cmp bx,0 ;G is a FOR in progress
jz no_bat_for ;G no - don't deallocate
push es ;G
mov es,bx ;G yes - free it up...
MOV AH,DEALLOC ;G
INT 21H ;G
pop es ;G restore to batch segment
no_bat_for:
mov cl,ES:[batechoflag] ;G get old echo flag
MOV BX,ES:[BATLAST] ;G get old batch segment
MOV AH,DEALLOC ; free it up...
INT 21H
MOV [BATCH],BX ;G get ready to deallocate next batch
DEC NEST ;G Is there another batch file?
JNZ CLEARBATCH ;G Keep going until no batch file
;
; We are terminating a batch file; restore the echo status
;
shell_bat_cont: ;AN000; continue batch for SHELL
POP BX ;G
MOV ECHOFLAG,CL ;G reset echo status
MOV PIPEFLAG,0 ;G turn off pipeflag
ContBatch:
invoke CRLF ;G print out crlf before returning
invoke RestHand
;
; Yes, we are terminating. Turn off flags and allow the DOS to abort.
;
CONTCTERM:
XOR AX,AX ; Indicate no read
MOV BP,AX
;
; The following resetting of the state flags is good for the generalized batch
; processing.
;
MOV IfFlag,AL ; turn off iffing
MOV [FORFLAG],AL ; Turn off for processing
call ResPipeOff
CMP [SINGLECOM],AX ; See if we need to set SINGLECOM
JZ NOSETSING
MOV [SINGLECOM],-1 ; Cause termination on pipe, batch, for
NOSETSING:
;
; If we are doing an internal command, go through the reload process. If we
; are doing an external, let DOS abort the process. In both cases, we are
; now done with the ^C processing.
;
AND InitFlag,NOT initCtrlC
CMP [EXTCOM],AL
JNZ DODAB ; Internal ^C
JMP LODCOM1
DODAB:
STC ; Tell DOS to abort
RET ; Leave flags on stack
ContC ENDP
public ResPipeOff
assume ds:nothing,es:nothing
ResPipeOff:
SaveReg <AX>
xor ax,ax
xchg PipeFlag,al
or al,al
jz NoPipePop
shr EchoFlag,1
NoPipePop:
RestoreReg <AX>
return
CODERES ENDS
END PROGSTART

View File

@ -0,0 +1,619 @@
page 80,132
; SCCSID = @(#)command2.asm 4.3 85/10/16
; SCCSID = @(#)command2.asm 4.3 85/10/16
TITLE COMMAND2 - resident code for COMMAND.COM part II
NAME COMMAND2
.XCREF
.XLIST
INCLUDE DOSSYM.INC
INCLUDE comsw.asm
INCLUDE comequ.asm
INCLUDE resmsg.equ ;AN000;
.LIST
.CREF
tokenized = FALSE
CODERES SEGMENT PUBLIC BYTE ;AC000;
CODERES ENDS
DATARES SEGMENT PUBLIC BYTE
EXTRN append_state:word ;AN020;
EXTRN append_flag:byte ;AN020;
EXTRN COMDRV:BYTE
EXTRN comprmt1_block:byte ;AN000;
EXTRN comprmt1_subst:byte ;AN000;
EXTRN COMSPEC:BYTE
EXTRN cpdrv:byte
EXTRN envirseg:word
EXTRN EXTCOM:BYTE
EXTRN HANDLE01:WORD
EXTRN InitFlag:BYTE
EXTRN INT_2E_RET:DWORD ;AC000;
EXTRN IO_SAVE:WORD
EXTRN LOADING:BYTE
EXTRN LTPA:WORD
EXTRN MEMSIZ:WORD
EXTRN number_subst:byte ;AN000;
EXTRN OldTerm:DWORD ;AC000;
EXTRN PARENT:WORD ;AC000;
EXTRN PERMCOM:BYTE
EXTRN RDIRCHAR:BYTE
EXTRN RES_TPA:WORD
EXTRN RETCODE:WORD
EXTRN rsrc_xa_seg:word ;AN030;
EXTRN RSWITCHAR:BYTE
EXTRN SAVE_PDB:WORD
EXTRN SINGLECOM:WORD
EXTRN SUM:WORD
EXTRN TRANS:WORD
EXTRN TranVarEnd:BYTE
EXTRN TRANVARS:BYTE
EXTRN TRNSEG:WORD
EXTRN VERVAL:WORD
DATARES ENDS
BATARENA SEGMENT PUBLIC PARA ;AC000;
BATARENA ENDS
BATSEG SEGMENT PUBLIC PARA ;AC000;
BATSEG ENDS
ENVARENA SEGMENT PUBLIC PARA ;AC000;
ENVARENA ENDS
ENVIRONMENT SEGMENT PUBLIC PARA ; Default COMMAND environment
ENVIRONMENT ENDS
INIT SEGMENT PUBLIC PARA
EXTRN envsiz:word
EXTRN oldenv:word
EXTRN resetenv:byte
EXTRN usedenv:word
INIT ENDS
TAIL SEGMENT PUBLIC PARA
TAIL ENDS
TRANCODE SEGMENT PUBLIC PARA
TRANCODE ENDS
TRANDATA SEGMENT PUBLIC BYTE
EXTRN TRANDATAEND:BYTE
TRANDATA ENDS
TRANSPACE SEGMENT PUBLIC BYTE
EXTRN TRANSPACEEND:BYTE
EXTRN HEADCALL:DWORD
TRANSPACE ENDS
TRANTAIL SEGMENT PUBLIC PARA
TRANTAIL ENDS
RESGROUP GROUP CODERES,DATARES,BATARENA,BATSEG,ENVARENA,ENVIRONMENT,INIT,TAIL
TRANGROUP GROUP TRANCODE,TRANDATA,TRANSPACE,TRANTAIL
; START OF RESIDENT PORTION
CODERES SEGMENT PUBLIC BYTE ;AC000;
PUBLIC CHKSUM
PUBLIC endinit
PUBLIC GETCOMDSK2
PUBLIC INT_2E
PUBLIC LOADCOM
PUBLIC LODCOM
PUBLIC LODCOM1
PUBLIC RESTHAND
PUBLIC SAVHAND
PUBLIC SETVECT
PUBLIC THEADFIX
PUBLIC TREMCHECK
PUBLIC tjmp
ASSUME CS:RESGROUP,DS:NOTHING,ES:NOTHING,SS:NOTHING
EXTRN contc:near
EXTRN DSKERR:NEAR
EXTRN rstack:word
;
; If we cannot allocate enough memory for the transient or there was some
; other allocation error, we display a message and then die.
;
BADMEMERR: ; Allocation error loading transient
MOV DX,BMEMMES ;AC000; get message number
FATALC:
PUSH CS
POP DS
ASSUME DS:ResGroup
invoke RPRINT
;
; If this is NOT a permanent (top-level) COMMAND, then we exit; we can't do
; anything else!
;
CMP PERMCOM,0
JZ FATALRET
;
; We are a permanent command. If we are in the process of the magic interrupt
; (Singlecom) then exit too.
;
CMP SINGLECOM,0 ; If PERMCOM and SINGLECOM
JNZ FATALRET ; Must take INT_2E exit
;
; Permanent command. We can't do ANYthing except halt.
;
MOV DX,HALTMES ;AC000; get message number
invoke RPRINT
STI
STALL:
JMP STALL ; Crash the system nicely
FATALRET:
MOV DX,FRETMES ;AC000; get message number
invoke RPRINT
FATALRET2:
CMP [PERMCOM],0 ; If we get here and PERMCOM,
JNZ RET_2E ; must be INT_2E
invoke reset_msg_pointers ;AN000; reset critical & parse error messages
MOV AX,[PARENT]
MOV WORD PTR CS:[PDB_Parent_PID],AX
MOV AX,WORD PTR OldTerm
MOV WORD PTR CS:[PDB_Exit],AX
MOV AX,WORD PTR OldTerm+2
MOV WORD PTR CS:[PDB_Exit+2],AX
MOV AX,(EXIT SHL 8) ; Return to lower level
INT int_command
RET_2E:
PUSH CS
POP DS
ASSUME DS:RESGROUP,ES:NOTHING,SS:NOTHING
MOV [SINGLECOM],0 ; Turn off singlecom
MOV ES,[RES_TPA]
MOV AH,DEALLOC
INT int_command ; Free up space used by transient
MOV BX,[SAVE_PDB]
MOV AH,SET_CURRENT_PDB
INT int_command ; Current process is user
MOV AX,[RETCODE]
CMP [EXTCOM],0
JNZ GOTECODE
XOR AX,AX ; Internals always return 0
GOTECODE:
MOV [EXTCOM],1 ; Force external
JMP [INT_2E_RET] ;"IRET"
INT_2E: ; Magic command executer
ASSUME DS:NOTHING,ES:NOTHING,SS:NOTHING
POP WORD PTR [INT_2E_RET]
POP WORD PTR [INT_2E_RET+2] ;Get return address
POP AX ;Chuck flags
PUSH CS
POP ES
MOV DI,80H
MOV CX,64
REP MOVSW
MOV AH,GET_CURRENT_PDB
INT int_command ; Get user's header
MOV [SAVE_PDB],BX
MOV AH,SET_CURRENT_PDB
MOV BX,CS
INT int_command ; Current process is me
MOV [SINGLECOM],81H
MOV [EXTCOM],1 ; Make sure this case forced
LODCOM: ; Termination handler
CMP [EXTCOM],0
jz lodcom1 ; if internal, memory already allocated
mov bx,0ffffh
MOV AH,ALLOC
INT int_command
CALL SetSize
ADD AX,20H
CMP BX,AX ; Is less than 512 byte buffer worth it?
JNC MEMOK
BADMEMERRJ:
JMP BADMEMERR ; Not enough memory
; SetSize - get transient size in paragraphs
Procedure SetSize,NEAR
MOV AX,OFFSET TRANGROUP:TRANSPACEEND + 15
MOV CL,4
SHR AX,CL
return
EndProc SetSize
MEMOK:
MOV AH,ALLOC
INT int_command
JC BADMEMERRJ ; Memory arenas probably trashed
MOV [EXTCOM],0 ; Flag not to ALLOC again
MOV [RES_TPA], AX ; Save current TPA segment
AND AX, 0F000H
ADD AX, 01000H ; Round up to next 64K boundary
JC BAD_TPA ; Memory wrap if carry set
; Make sure that new boundary is within allocated range
MOV DX, [RES_TPA]
ADD DX, BX ; Compute maximum address
CMP DX, AX ; Is 64K address out of range?
JBE BAD_TPA
; Must have 64K of usable space.
SUB DX, AX ; Compute the usable space
CMP DX, 01000H ; Is space >= 64K ?
JAE LTPASET
BAD_TPA:
MOV AX, [RES_TPA]
LTPASET:
MOV [LTPA],AX ; Usable TPA is 64k buffer aligned
MOV AX, [RES_TPA] ; Actual TPA is buffer allocated
ADD BX,AX
MOV [MEMSIZ],BX
CALL SetSize
SUB BX,AX
MOV [TRNSEG],BX ; Transient starts here
LODCOM1:
MOV AX,CS
MOV SS,AX
ASSUME SS:RESGROUP
MOV SP,OFFSET RESGROUP:RSTACK
MOV DS,AX
ASSUME DS:RESGROUP
CALL HEADFIX ; Make sure files closed stdin and stdout restored
XOR BP,BP ; Flag command ok
MOV AX,-1
XCHG AX,[VERVAL]
CMP AX,-1
JZ NOSETVER
MOV AH,SET_VERIFY_ON_WRITE ; AL has correct value
INT int_command
NOSETVER:
CMP [SINGLECOM],-1
JNZ NOSNG
JMP FATALRET2 ; We have finished the single command
NOSNG:
CALL CHKSUM ; Check the transient
CMP DX,[SUM]
JZ HAVCOM ; Transient OK
BOGUS_COM:
MOV [LOADING],1 ; Flag DSKERR routine
CALL LOADCOM
CHKSAME:
CALL CHKSUM
CMP DX,[SUM]
JZ HAVCOM ; Same COMMAND
ALSO_BOGUS:
CALL WRONGCOM
JMP SHORT CHKSAME
HAVCOM:
MOV AX,CHAR_OPER SHL 8
INT int_command
MOV [RSWITCHAR],DL
CMP DL,'/'
JNZ USESLASH
mov cl,'\'
MOV [RDIRCHAR],cl ; Select alt path separator
USESLASH:
MOV [LOADING],0 ; Flag to DSKERR
MOV SI,OFFSET RESGROUP:TRANVARS
MOV DI,OFFSET TRANGROUP:HEADCALL
MOV ES,[TRNSEG]
CLD
MOV CX,OFFSET ResGroup:TranVarEnd
SUB CX,SI
REP MOVSB ; Transfer INFO to transient
MOV AX,[MEMSIZ]
MOV WORD PTR DS:[PDB_block_len],AX ; Adjust my own header
; Just a public label so this spot can be found easily.
tjmp:
JMP DWORD PTR [TRANS]
; Far call to REMCHECK for TRANSIENT
TREMCHECK PROC FAR
CALL REMCHECK
RET
TREMCHECK ENDP
REMCHECK:
;All registers preserved. Returns ZF set if media removable, NZ if fixed
; AL is drive (0=DEF, 1=A,...).
SaveReg <AX,BX>
MOV BX,AX
MOV AX,(IOCTL SHL 8) + 8
INT 21h
jnc RCcont ; If an error occurred, assume the media
or ax,ax ; is NON-removable.
; AX contains the non-zero error code
; from the INT 21, so the OR AX,AX sets
; Non-zero. This behavior makes Network
; drives appear to be non-removable.
jmp SHORT ResRegs
RCcont:
AND AX,1
NOT AX
ResRegs:
RestoreReg <BX,AX>
return
; Far call to HEADFIX for TRANSIENT
THEADFIX PROC FAR
CALL HEADFIX
RET
THEADFIX ENDP
HEADFIX:
CALL SETVECT
XOR BX,BX ; Clean up header
MOV CX,[IO_SAVE]
MOV DX,WORD PTR DS:[PDB_JFN_Table]
CMP CL,DL
JZ CHK1 ; Stdin matches
MOV AH,CLOSE
INT int_command
MOV DS:[PDB_JFN_Table],CL ; Restore stdin
CHK1:
INC BX
CMP CH,DH ; Stdout matches
JZ CHKOTHERHAND
MOV AH,CLOSE
INT int_command
MOV DS:[PDB_JFN_Table+1],CH ; Restore stdout
CHKOTHERHAND:
ADD BX,4 ; Skip 2,3,4
MOV CX,FilPerProc - 5 ; Already done 0,1,2,3,4
CLOSELOOP:
MOV AH,CLOSE
INT int_command
INC BX
LOOP CLOSELOOP
push ds ;AN020; save data segment
push cs ;AN020; Get local segment into DS
pop ds ;AN020;
cmp append_flag,-1 ;AN020; Do we need to reset APPEND?
jnz append_fix_end ;AN030; no - just exit
mov ax,AppendSetState ;AN020; Set the state of Append
mov bx,Append_state ;AN020; back to the original state
int 2fh ;AN020;
mov append_flag,0 ;AN020; Set append flag to invalid
append_fix_end: ;AN030;
cmp [rsrc_xa_seg],no_xa_seg ;AN030; Is there any active XA segment?
jz xa_fix_end ;AN030; no - exit
push es ;AN030; Yes - deallocate it
mov es,rsrc_xa_seg ;AN030;
mov ax,(Dealloc SHL 8) ;AN030; Deallocate memory call
int int_command ;AN030;
pop es ;AN030;
mov [rsrc_xa_seg],no_xa_seg ;AN030; reset to no segment
xa_fix_end:
pop ds ;AN020; get data segment back
return
SAVHAND:
ASSUME DS:NOTHING,ES:NOTHING,SS:NOTHING
PUSH DS
PUSH BX ; Set stdin to sterr, stdout to stderr
PUSH AX
MOV AH,GET_CURRENT_PDB
INT int_command ; Get user's header
MOV DS,BX
LDS BX,DS:[PDB_JFN_POINTER] ; get pointer to JFN table...
MOV AX,WORD PTR DS:[BX]
MOV [HANDLE01],AX ; Save user's stdin, stdout
MOV AL,CS:[PDB_JFN_Table+2] ; get COMMAND stderr
MOV AH,AL
MOV WORD PTR DS:[BX],AX ; Dup stderr
POP AX
POP BX
POP DS
return
ASSUME DS:RESGROUP
GETCOMDSK2:
CALL GETCOMDSK
JMP LODCOM1 ; Memory already allocated
RESTHAND:
PUSH DS
PUSH BX ; Restore stdin, stdout to user
PUSH AX
MOV AH,GET_CURRENT_PDB
INT int_command ; Point to user's header
MOV AX,[HANDLE01]
MOV DS,BX
ASSUME DS:NOTHING
LDS BX,DS:[PDB_JFN_POINTER] ; get pointer to JFN table...
MOV WORD PTR DS:[BX],AX ; Stuff his old 0 and 1
POP AX
POP BX
POP DS
return
ASSUME DS:RESGROUP,SS:RESGROUP
HOPELESS:
MOV DX,COMBAD ;AC000;
JMP FATALC
GETCOMDSK:
mov al,[comdrv]
CALL REMCHECK
jNZ HOPELESS ;Non-removable media
getcomdsk3:
cmp dx,combad ;AC000;
jnz getcomdsk4
mov dx,combad ;AN000; get message number
invoke RPRINT ; Say command is invalid
getcomdsk4:
cmp [cpdrv],0 ;g is there a drive in the comspec?
jnz users_drive ;g yes - use it
mov ah,Get_default_drive ;g use default drive
int 21h ;g
add al,"A" ;g convert to ascii
mov [cpdrv],al ;g put in message to print out
users_drive: ;g
mov dx,comprmt1 ;AC000; Prompt for diskette containing command
IF tokenized
or byte ptr [si],80h
endif
MOV AL,COMPRMT1_SUBST ;AN000; get number of substitutions
MOV SI,OFFSET RESGROUP:COMPRMT1_BLOCK ;AN000; get address of subst block
MOV NUMBER_SUBST,AL ;AN000;
invoke rprint
if tokenized
and byte ptr [si],NOT 80h
endif
mov dx,prompt ;AN047; Tell the user to strike a key
invoke rprint ;AN047;
CALL GetRawFlushedByte
return
; flush world and get raw input
GetRawFlushedByte:
MOV AX,(STD_CON_INPUT_FLUSH SHL 8) OR RAW_CON_INPUT
INT int_command ; Get char without testing or echo
MOV AX,(STD_CON_INPUT_FLUSH SHL 8) + 0
INT int_command
return
LOADCOM: ; Load in transient
INC BP ; Flag command read
MOV DX,OFFSET RESGROUP:COMSPEC
MOV AX,OPEN SHL 8
INT int_command ; Open COMMAND.COM
JNC READCOM
CMP AX,error_too_many_open_files
JNZ TRYDOOPEN
MOV DX,NOHANDMES ;AC000;
JMP FATALC ; Fatal, will never find a handle
TRYDOOPEN:
CALL GETCOMDSK
JMP LOADCOM
READCOM:
MOV BX,AX ; Handle
MOV DX,OFFSET RESGROUP:TRANSTART
XOR CX,CX ; Seek loc
MOV AX,LSEEK SHL 8
INT int_command
JC WRONGCOM1
MOV CX,OFFSET TRANGROUP:TRANSPACEEND - 100H
PUSH DS
MOV DS,[TRNSEG]
ASSUME DS:NOTHING
MOV DX,100H
MOV AH,READ
INT int_command
POP DS
ASSUME DS:RESGROUP
WRONGCOM1:
PUSHF
PUSH AX
MOV AH,CLOSE
INT int_command ; Close COMMAND.COM
POP AX
POPF
JC WRONGCOM ; If error on READ
CMP AX,CX
retz ; Size matched
WRONGCOM:
MOV DX,COMBAD ;AC000;
CALL GETCOMDSK
JMP LOADCOM ; Try again
CHKSUM: ; Compute transient checksum
PUSH DS
MOV DS,[TRNSEG]
MOV SI,100H
MOV CX,OFFSET TRANGROUP:TranDataEnd - 100H
CHECK_SUM:
CLD
SHR CX,1
XOR DX,DX
CHK:
LODSW
ADD DX,AX
ADC DX,0
LOOP CHK
POP DS
return
SETVECT: ; Set useful vectors
MOV DX,OFFSET RESGROUP:LODCOM
MOV AX,(SET_INTERRUPT_VECTOR SHL 8) OR 22H
MOV WORD PTR DS:[PDB_EXIT],DX
MOV WORD PTR DS:[PDB_EXIT+2],DS
INT int_command
MOV DX,OFFSET RESGROUP:CONTC
INC AL
INT int_command
MOV DX,OFFSET RESGROUP:DSKERR
INC AL
INT int_command
return
;
; This routine moves the environment to a newly allocated segment
; at the end of initialization
;
ENDINIT:
push ds ;g save segments
push es ;g
push cs ;g get resident segment to DS
pop ds ;g
ASSUME DS:RESGROUP
mov cx,usedenv ;g get number of bytes to move
mov es,envirseg ;g get target environment segment
ASSUME ES:NOTHING
mov DS:[PDB_environ],es ;g put new environment in my header ;AM067;
mov ds,oldenv ;g source environment segment ;AM067;
ASSUME DS:NOTHING ;AM067;
xor si,si ;g set up offsets to start of segments ;AM067;
xor di,di ;g ;AM067;
cld ;g make sure we move the right way! ;AM067;
rep movsb ;g move it ;AM067;
xor ax,ax ;g ;AM067;
stosb ;g make sure there are double 0 at end ;AM067;
cmp resetenv,1 ;eg Do we need to setblock to env end?
jnz noreset ;eg no - we already did it
mov bx,envsiz ;eg get size of environment in paragraphs
push es ;eg save environment - just to make sure
mov ah,SETBLOCK ;eg
int int_command ;eg
pop es ;eg
noreset:
mov InitFlag,FALSE ;AC042; Turn off init flag
pop es ;g
pop ds ;g
jmp lodcom ;g allocate transient
CODERES ENDS
; This TAIL segment is used to produce a PARA aligned label in the resident
; group which is the location where the transient segments will be loaded
; initial.
TAIL SEGMENT PUBLIC PARA
ORG 0
PUBLIC TranStart
TRANSTART LABEL WORD
TAIL ENDS
; This TAIL segment is used to produce a PARA aligned label in the transient
; group which is the location where the exec segments will be loaded
; initial.
TRANTAIL SEGMENT PUBLIC PARA
ORG 0
EXECSTART LABEL WORD
TRANTAIL ENDS
END

View File

@ -0,0 +1,43 @@
; SCCSID = @(#)comseg.asm 1.1 85/05/14
; SCCSID = @(#)comseg.asm 1.1 85/05/14
; The following are all of the segments used in the load order
CODERES SEGMENT PUBLIC BYTE ;AC000; resident code
CODERES ENDS
DATARES SEGMENT PUBLIC BYTE ;AC000; resident data
DATARES ENDS
BATARENA SEGMENT PUBLIC PARA ;AC000; space for DOS ALLOCATE header
BATARENA ENDS
BATSEG SEGMENT PUBLIC PARA ;AC000; AUTOEXEC batch segment
BATSEG ENDS
ENVARENA SEGMENT PUBLIC PARA ;AC000; space for DOS ALLOCATE header
ENVARENA ENDS
ENVIRONMENT SEGMENT PUBLIC PARA ;AC000; Default COMMAND environment
ENVIRONMENT ENDS
INIT SEGMENT PUBLIC PARA ;AC000; Initialization code
INIT ENDS
TAIL SEGMENT PUBLIC PARA ;AC000; End of Init - start of Transient
TAIL ENDS
TRANCODE SEGMENT PUBLIC BYTE ;AC000; Transient code
TRANCODE ENDS
TRANDATA SEGMENT PUBLIC BYTE ;AC000; Transient data area
TRANDATA ENDS
TRANSPACE SEGMENT PUBLIC BYTE ;AC000; Transient modifiable data area
TRANSPACE ENDS
TRANTAIL SEGMENT PUBLIC PARA ;AC000; End of Transient
TRANTAIL ENDS
RESGROUP GROUP CODERES,DATARES,BATARENA,BATSEG,ENVARENA,ENVIRONMENT,INIT,TAIL
TRANGROUP GROUP TRANCODE,TRANDATA,TRANSPACE,TRANTAIL


Some files were not shown because too many files have changed in this diff Show More