summaryrefslogtreecommitdiff
path: root/v2.0/source/CHKDSK.ASM
diff options
context:
space:
mode:
authorGravatar Rich Turner1983-08-12 17:53:34 -0700
committerGravatar Rich Turner2018-09-21 17:53:34 -0700
commit80ab2fddfdf30f09f0a0a637654cbb3cd5c7baa6 (patch)
treeee4357f7f3dd0f2ded59b9c6e7384432d85e7ec9 /v2.0/source/CHKDSK.ASM
parentMS-DOS v1.25 Release (diff)
downloadms-dos-80ab2fddfdf30f09f0a0a637654cbb3cd5c7baa6.tar.gz
ms-dos-80ab2fddfdf30f09f0a0a637654cbb3cd5c7baa6.tar.xz
ms-dos-80ab2fddfdf30f09f0a0a637654cbb3cd5c7baa6.zip
MS-DOS v2.0 Release
Diffstat (limited to 'v2.0/source/CHKDSK.ASM')
-rw-r--r--v2.0/source/CHKDSK.ASM901
1 files changed, 901 insertions, 0 deletions
diff --git a/v2.0/source/CHKDSK.ASM b/v2.0/source/CHKDSK.ASM
new file mode 100644
index 0000000..c305a1d
--- /dev/null
+++ b/v2.0/source/CHKDSK.ASM
@@ -0,0 +1,901 @@
1TITLE CHKDSK - MS-DOS Disk consistancy checker
2
3; CHKDSK Version 2.30
4; Verifies and repairs MS-DOS disk directory.
5
6
7; To build CHKDSK you need three modules:
8; CHKDSK CHKPROC CHKMES
9; They should be linked the that order as well.
10
11
12; REVISION HISTORY
13
14;REV 1.1
15; 05/21/82 Added rev number
16
17;REV 1.5
18; Mod by NANCYP to report on extents
19; Mod by AARONR to report volume ID
20
21;REV 2.0
22; Total rewrite for directories
23
24;REV 2.1
25; Added ^C and INT 24H handlers
26
27;REV 2.2
28; INTERNATIONAL support
29
30;REV 2.3
31; Split into two modules to allow assembly on a PC
32; CHKDSK and CHKPROC
33
34FALSE EQU 0
35TRUE EQU NOT FALSE
36
37DRVCHAR EQU ":"
38
39;The following defines the ranges of DOS version numbers for which this CHKDSK
40; is good
41
42DOSVER_LOW EQU 0136H ;1.54 in hex
43DOSVER_HIGH EQU 020BH ;2.11 in hex
44
45
46 INCLUDE DOSSYM.ASM
47
48FCB EQU 5CH
49
50;Drive parameter block from DOS header
51
52SUBTTL Segments used in load order
53
54CODE SEGMENT PUBLIC
55CODE ENDS
56
57CONST SEGMENT PUBLIC BYTE
58CONST ENDS
59
60DATA SEGMENT PUBLIC WORD
61DATA ENDS
62
63DG GROUP CODE,CONST,DATA
64
65SUBTTL Initialized Data
66PAGE
67CONST SEGMENT PUBLIC BYTE
68
69 PUBLIC HECODE,SWITCHAR,NOISY,DOFIX,CONBUF,ORPHCNT,ORPHSIZ,DOFIX
70 PUBLIC HIDCNT,HIDSIZ,DIRCNT,DIRSIZ,FILCNT,FILSIZ,BADSIZ,LCLUS
71 PUBLIC DOTENT,HAVFIX,SECONDPASS,NUL,ALLFILE,PARSTR,ERRSUB,LCLUS
72 PUBLIC DIRTYFAT,BADSIZ,DDOTENT,CROSSCNT,ORPHFCB,ORPHEXT,ALLDRV
73 PUBLIC FRAGMENT,USERDIR,DIRBUF,USERDIR,FIXMFLG,DOTMES,DIRCHAR
74
75 EXTRN IDMES1:BYTE,IDPOST:BYTE,VNAME:BYTE,MONTAB:BYTE
76 EXTRN TCHAR:BYTE,BADREAD_PRE:BYTE,BADREAD_POST:BYTE
77 EXTRN CRLF:BYTE,BADVER:BYTE,BADSUBDIR:BYTE,CENTRY:BYTE
78 EXTRN BADDRV:BYTE,BADCD:BYTE,BADRDMES:BYTE,OPNERR:BYTE
79 EXTRN CONTAINS:BYTE,EXTENTS:BYTE,NOEXTENTS:BYTE
80 EXTRN BADDRVM:BYTE,BADDRVM2:BYTE,BADIDBYT:BYTE
81
82
83DIRBUF LABEL BYTE ;Entry buffer for searches
84VOLID DB -1,0,0,0,0,0,8 ;Volume ID FCB
85VOLNAM DB 0,"???????????"
86 DB 25 DUP(0)
87
88ALLFILE DB -1,0,0,0,0,0,1EH ;Extended FCB
89ALLDRV DB 0,"???????????"
90 DB 25 DUP (?)
91
92ORPHFCB DB 0,"FILE0000"
93ORPHEXT DB "CHK"
94 DB 25 DUP (?)
95
96
97;Non-message data
98
99SWITCHAR DB "-"
100ROOTSTR LABEL BYTE
101DIRCHAR DB "/"
102NUL DB 0
103PARSTR DB "..",0
104DOTMES DB ".",0
105DOTENT DB ". "
106DDOTENT DB ".. "
107HECODE DB ?
108FIXMFLG DB 0 ;Flag for printing fixmes
109ERRSUB DW 0 ;Flag for bad subdir error
110FRAGMENT DB 0 ;Flag for extent processing
111DIRTYFAT DB 0 ;Dirty flag for FAT
112DIRCNT DW 0 ;# directories
113DIRSIZ DW 0 ;# alloc units in directories
114FILCNT DW 0 ;# reg files
115FILSIZ DW 0 ;# alloc units in reg files
116HIDCNT DW 0 ;# hidden files
117HIDSIZ DW 0 ;# alloc units in hidden files
118BADSIZ DW 0 ;# alloc units in bad sectors
119ORPHCNT DW 0 ;# orphan files made
120ORPHSIZ DW 0 ;# alloc units in orphan files
121LCLUS DW 0 ;# alloc units in lost clusters
122DISPFLG DB 0 ;used by number routines
123CROSSCNT DW 0 ;# crosslinked files (first pass)
124SECONDPASS DB 0 ;Pass flag
125HAVFIX DB 0 ;non zero if any fixes
126DOFIX DB 0 ;flag for F switch
127NOISY DB 0 ;flag for V switch
128USERDIR DB "/",0 ;Users current dir for drive
129 DB (DIRSTRLEN-1) DUP (?)
130CONBUF DB 15,0 ;Input buffer
131 DB 15 DUP (?)
132
133CONST ENDS
134
135SUBTTL Un-initialized Data
136PAGE
137DATA SEGMENT PUBLIC WORD
138
139 PUBLIC ZEROTRUNC,NAMBUF,MCLUS,THISDPB,STACKLIM,ERRCNT
140 PUBLIC SRFCBPT,ISCROSS,CSIZE,DSIZE,SSIZE,FAT,FATMAP
141 PUBLIC HARDCH,CONTCH,USERDEV,SECBUF,DOTSNOGOOD
142
143HARDCH DD ? ;Pointer to real INT 24 handler
144CONTCH DD ? ;Pointer to real INT 23 handler
145THISDPB DD ? ;Pointer to drive DPB
146USERDEV DB ? ;Users current device
147CSIZE DB ? ;Sectors per cluster
148SSIZE DW ? ;bytes per sector
149DSIZE DW ? ;# alloc units on disk
150MCLUS DW ? ;DSIZE + 1
151NAMBUF DB 14 DUP (?) ;Buffer
152DOTSNOGOOD DB ? ;. or .. error flag
153ZEROTRUNC DB ? ;Trimming flag
154ISCROSS DB ? ;Crosslink flag
155OLDCLUS DW ?
156SRFCBPT DW ?
157FATMAP DW OFFSET DG:FAT ;Offset of FATMAP table
158SECBUF DW ? ;Offset of sector buffer
159ERRCNT DB ? ;Used by FATread and write
160STACKLIM DW ? ;Stack growth limit
161
162INTERNATVARS internat_block <>
163 DB (internat_block_max - ($ - INTERNATVARS)) DUP (?)
164
165FAT LABEL WORD
166DATA ENDS
167
168
169SUBTTL Start of CHKDSK
170
171CODE SEGMENT PUBLIC
172ASSUME CS:DG,DS:DG,ES:DG,SS:DG
173
174 PUBLIC SUBERRP,DOTCOMBMES,FIGREC,FCB_TO_ASCZ,PRTCHR,EPRINT
175 PUBLIC PRINT,DOCRLF,DISP16BITS,DISP32BITS,DISPCLUS,CHECKFILES
176
177 EXTRN RDSKERR:NEAR,SETSWITCH:NEAR,PROMPTYN:NEAR,REPORT:NEAR
178 EXTRN PRINTCURRDIRERR:NEAR,PRINTTHISEL2:NEAR,CHECKERR:NEAR
179 EXTRN INT_23:NEAR,INT_24:NEAR,FINDCHAIN:NEAR,DONE:NEAR,AMDONE:NEAR
180 EXTRN FATAL:NEAR,DIRPROC:NEAR,CHKMAP:NEAR,CHKCROSS:NEAR,UNPACK:NEAR
181
182 ORG 100H
183
184CHKDSK:
185 JMP SHORT CHSTRT
186
187HEADER DB "Ver 2.30"
188
189CHSTRT:
190
191;Code to print header.
192; PUSH AX
193; MOV DX,OFFSET DG:HEADER
194; CALL PRINT
195; POP AX
196
197 PUSH AX ;Save DRIVE validity info
198 MOV AH,GET_VERSION
199 INT 21H
200 XCHG AH,AL ;Turn it around to AH.AL
201 CMP AX,DOSVER_LOW
202 JB GOTBADDOS
203 CMP AX,DOSVER_HIGH
204 JBE OKDOS
205GOTBADDOS:
206 MOV DX,OFFSET DG:BADVER
207 JMP CERROR
208
209OKDOS:
210 POP AX ;Get back drive info
211 MOV BX,0FFF0H
212 MOV DX,SP
213 CMP DX,BX
214 JAE STACKOK ;Lots of stack
215 MOV DX,DS:[2] ;High break
216 MOV CX,CS
217 SUB DX,CX
218 CMP DX,0FFFH
219 JAE SETSTACK ;Lots to grab
220 MOV CX,4 ;Suck up more stack (blast command)
221 SHL DX,CL
222 MOV BX,DX
223SETSTACK:
224 CLI
225 MOV SP,BX
226 STI
227STACKOK:
228 PUSH AX
229 MOV AH,DISK_RESET ;Flush everything, and invalidate
230 INT 21H
231 POP AX
232 CMP AL,0FFH ;Illegal drive specifier?
233 JNZ FILECHK ;No -- check for filename
234
235DRVERR:
236 MOV DX,OFFSET DG:BADDRV
237CERROR:
238 PUSH CS ;Make sure DS is OK
239 POP DS
240 CALL PRINT ;Print error message
241 INT 20H
242
243CERROR2:
244 PUSH DX
245 CALL DONE ;Reset users disk
246 POP DX
247 JMP SHORT CERROR
248
249FILECHK:
250 MOV AX,(CHAR_OPER SHL 8)
251 INT 21H
252 MOV [SWITCHAR],DL
253 CMP DL,"/"
254 JNZ SLASHOK
255 MOV [DIRCHAR],"\"
256 MOV [USERDIR],"\"
257SLASHOK:
258 CMP DS:(BYTE PTR FCB+1)," " ;Filename specified?
259 JZ DRVCHK ;No -- get the correct drive
260 MOV AL,[SWITCHAR]
261 CMP DS:(BYTE PTR FCB+1),AL ;Filename specified?
262 JZ DRVCHK ;No -- get the correct drive
263 MOV BYTE PTR [FRAGMENT],1 ;Set flag to perform fragment
264 ;check on specified files
265DRVCHK:
266 CALL SETSWITCH ;Look for switches
267 MOV AH,GET_DEFAULT_DRIVE ;Get current drive
268 INT 21H
269 MOV [USERDEV],AL ;Save for later
270 MOV AH,AL
271 INC AH ;A = 1
272 MOV BH,DS:(BYTE PTR FCB) ;See if drive specified
273 OR BH,BH
274 JZ SETDSK
275 MOV AL,BH
276 MOV AH,AL
277 DEC AL ;A = 0
278SETDSK:
279 MOV [ALLDRV],AH ;Target drive
280 MOV [VOLNAM],AH ;A = 1
281 MOV [ORPHFCB],AH ;A = 1
282 ADD [BADDRVM],AL ;A = 0
283 ADD [BADDRVM2],AL ;A = 0
284 MOV DL,AH ;A = 1
285 MOV AH,GET_DPB ;Get the DPB
286 INT 21H
287ASSUME DS:NOTHING
288 CMP AL,-1
289 JNZ DRVISOK ;Bad drive (should always be ok)
290 MOV DX,OFFSET DG:BADDRV
291CERROR2J: JMP CERROR2
292
293DRVISOK:
294 DEC DL ;A = 0
295 MOV AH,SET_DEFAULT_DRIVE ;Set Target
296 INT 21H
297 CMP [BX.dpb_current_dir],0
298 JZ CURRISROOT ;Save users current dir for target
299 MOV SI,BX
300 ADD SI,dpb_dir_text
301 MOV DI,OFFSET DG:USERDIR + 1
302SETDIRLP:
303 LODSB
304 STOSB
305 OR AL,AL
306 JZ CURRISROOT
307 JMP SHORT SETDIRLP
308CURRISROOT:
309 MOV WORD PTR [THISDPB+2],DS
310 PUSH CS
311 POP DS
312ASSUME DS:DG
313 MOV WORD PTR [THISDPB],BX
314 MOV AX,(GET_INTERRUPT_VECTOR SHL 8) OR 23H
315 INT 21H
316 MOV WORD PTR [CONTCH],BX
317 MOV WORD PTR [CONTCH+2],ES
318 MOV AX,(SET_INTERRUPT_VECTOR SHL 8) OR 23H
319 MOV DX,OFFSET DG:INT_23
320 INT 21H
321 MOV AX,(GET_INTERRUPT_VECTOR SHL 8) OR 24H
322 INT 21H
323 MOV WORD PTR [HARDCH],BX
324 MOV WORD PTR [HARDCH+2],ES
325 MOV AX,(SET_INTERRUPT_VECTOR SHL 8) OR 24H
326 MOV DX,OFFSET DG:INT_24
327 INT 21H
328 PUSH CS
329 POP ES
330 MOV DX,OFFSET DG:ROOTSTR
331 MOV AH,CHDIR ;Start at root
332 INT 21H
333 MOV DX,OFFSET DG:BADCD
334 JC CERROR2J ;Couldn't get there
335 MOV DX,OFFSET DG:FAT ;Scratch space
336 MOV AH,SET_DMA
337 INT 21H
338 MOV DX,OFFSET DG:VOLID ;Look for VOL ID
339 MOV AH,DIR_SEARCH_FIRST
340 INT 21H
341 CMP AL,-1
342 JZ NOTVOLID
343 CALL PRINTID ;Have a VOL ID
344NOTVOLID:
345 LDS BX,[THISDPB]
346ASSUME DS:NOTHING
347 MOV AX,[BX.dpb_sector_size]
348 MOV [SSIZE],AX ;Sector size in bytes
349 MOV AL,[BX.dpb_cluster_mask]
350 INC AL
351 MOV [CSIZE],AL ;Sectros per cluster
352 MOV AX,[BX.dpb_max_cluster]
353 MOV [MCLUS],AX ;Bound for FAT searching
354 DEC AX
355 MOV [DSIZE],AX ;Total data clusters on disk
356 MOV AL,[BX.dpb_FAT_size] ;Sectors for one fat
357 XOR AH,AH
358 MOV CX,AX
359 MUL [SSIZE] ;Bytes for FAT
360 ADD [FATMAP],AX ;Allocate FAT space
361 MOV AX,[FATMAP]
362 ADD AX,[MCLUS]
363 ADD AX,2 ;Insurance
364 MOV [SECBUF],AX ;Allocate FATMAP space
365 ADD AX,[SSIZE]
366 ADD AX,20 ;Insurance
367 MOV [STACKLIM],AX ;Limit on recursion
368 MOV DI,CX
369 MOV CL,[BX.dpb_FAT_count] ;Number of FATs
370 MOV DX,[BX.dpb_first_FAT] ;First sector of FAT
371 PUSH CS
372 POP DS
373ASSUME DS:DG
374 MOV BX,OFFSET DG:FAT
375 MOV AL,[ALLDRV]
376 DEC AL
377 MOV AH,'1'
378RDLOOP:
379 XCHG CX,DI
380 PUSH DX
381 PUSH CX
382 PUSH DI
383 PUSH AX
384 INT 25H ;Read in the FAT
385 MOV [HECODE],AL
386 POP AX ;Flags
387 JNC RDOK
388 MOV DX,OFFSET DG:BADREAD_PRE ;Barfed
389 CALL PRINT
390 POP AX
391 PUSH AX
392 MOV DL,AH
393 CALL PRTCHR
394 MOV DX,OFFSET DG:BADREAD_POST
395 CALL PRINT
396 POP AX
397 POP CX
398 POP DI
399 POP DX
400 INC AH
401 ADD DX,DI
402 LOOP RDLOOP ;Try next FAT
403 CALL RDSKERR
404 JNZ NORETRY1
405 JMP NOTVOLID
406NORETRY1:
407 MOV BX,OFFSET DG:BADRDMES
408 JMP FATAL ;Couldn't read any FAT, BARF
409
410RDOK:
411 POP AX ;Clean up
412 POP AX
413 POP AX
414 POP AX
415 MOV SI,OFFSET DG:FAT
416 LODSB ;Check FAT ID byte
417 CMP AL,0F8H
418 JAE IDOK
419 MOV DX,OFFSET DG:BADIDBYT ;FAT ID bad
420 CALL PROMPTYN ;Ask user
421 JZ IDOK
422 JMP ALLDONE ;User said stop
423IDOK:
424 MOV DI,[FATMAP]
425 MOV CX,[MCLUS]
426 INC CX
427 XOR AL,AL
428 REP STOSB ;Initialize FATMAP to all free
429 MOV DX,OFFSET DG:DIRBUF ;FOR ALL SEARCHING
430 MOV AH,SET_DMA
431 INT 21H
432 XOR AX,AX
433 PUSH AX ;I am root
434 PUSH AX ;Parent is root
435 CALL DIRPROC
436 CALL CHKMAP ;Look for badsectors, orphans
437 CALL CHKCROSS ;Check for second pass
438 CALL DOCRLF
439 CALL REPORT
440
441ALLDONE:
442 CALL AMDONE
443 INT 20H ;Fini
444
445
446ASSUME DS:DG
447
448SUBTTL Check for extents in specified files
449PAGE
450CHECKFILES:
451;Search the directory for the files specified on the command line
452;and report the number of fragmented allocation units found in
453;each one.
454 CALL DOCRLF
455 MOV AH,SET_DMA
456 MOV DX,[FATMAP] ;Use the first free space available
457 MOV BP,DX
458 ADD BP,27 ;cluster in the directory entry
459 INT 21H
460 MOV AH,DIR_SEARCH_FIRST ;Look for the first file
461FRAGCHK:
462 MOV DX,FCB
463 INT 21H
464 OR AL,AL ;Did we find it?
465 JNZ MSGCHK ;No -- we're done
466 XOR AX,AX ;Initialize the fragment counter
467 MOV SI,[BP] ;Get the first cluster
468 CALL UNPACK
469 CMP DI,0FF8H ;End-of-file?
470 JAE NXTCHK ;Yes -- go report the results
471 INC SI
472 CMP SI,DI
473 JZ EACHCLUS
474 INC AX
475EACHCLUS:
476 MOV [OLDCLUS],DI ;Save the last cluster found
477 MOV SI,DI ;Get the next cluster
478 CALL UNPACK
479 INC [OLDCLUS] ;Bump the old cluster
480 CMP DI,[OLDCLUS] ;Are they the same?
481 JNZ LASTCLUS ;No -- check for end-of-file
482 JMP SHORT EACHCLUS ;Continue processing
483LASTCLUS:
484 CMP DI,0FF8H ;End-of-file?
485 JAE NXTCHK ;Yes -- go report the results
486 INC AX ;No -- found a fragement
487 JMP SHORT EACHCLUS ;Continue processing
488
489NXTCHK:
490 OR AX,AX
491 JZ GETNXT
492 MOV [FRAGMENT],2 ;Signal that we output at least one file
493 PUSH AX ;Save count of fragments
494 MOV SI,[FATMAP]
495 INC SI
496 CALL PRINTTHISEL2
497 CALL DOCRLF
498 MOV DX,OFFSET DG:CONTAINS ;Print message
499 CALL PRINT
500 POP SI ;Number of fragments found
501 INC SI ;Number non-contig blocks
502 XOR DI,DI
503 MOV BX,OFFSET DG:EXTENTS
504 PUSH BP
505 CALL DISP16BITS
506 POP BP
507GETNXT:
508 MOV AH,DIR_SEARCH_NEXT ;Look for the next file
509 JMP FRAGCHK
510
511MSGCHK:
512 CMP AH,DIR_SEARCH_FIRST
513 JNZ FILSPOK
514 MOV SI,FCB + 1 ;File not found error
515 CALL PRINTTHISEL2
516 CALL DOCRLF
517 MOV DX,OFFSET DG:OPNERR
518 CALL PRINT ;Bad file spec
519 RET
520FILSPOK:
521 CMP BYTE PTR [FRAGMENT],2
522 JZ CDONE
523 MOV DX,OFFSET DG:NOEXTENTS
524 CALL PRINT
525CDONE:
526 RET
527
528
529FIGREC:
530;Convert cluster number in BX to sector # AH of cluster in DX
531 LDS DI,[THISDPB]
532ASSUME DS:NOTHING
533 MOV CL,[DI.dpb_cluster_shift]
534 MOV DX,BX
535 DEC DX
536 DEC DX
537 SHL DX,CL
538 OR DL,AH
539 ADD DX,[DI.dpb_first_sector]
540 PUSH CS
541 POP DS
542ASSUME DS:DG
543 RET
544
545
546SUBTTL PRINTID - Print Volume ID info
547PAGE
548PRINTID:
549ASSUME DS:DG
550 MOV DX,OFFSET DG:INTERNATVARS
551 MOV AX,INTERNATIONAL SHL 8
552 INT 21H
553 MOV [DISPFLG],1 ;Don't sub spaces for leading zeros
554 MOV SI,OFFSET DG:FAT + 8
555 MOV DI,OFFSET DG:VNAME
556 MOV CX,11
557 REP MOVSB
558 MOV DX,OFFSET DG:IDMES1
559 CALL PRINT ;Print ID message
560 ADD SI,13
561 LODSW ;Get date
562 PUSH SI
563 MOV DX,AX
564 MOV AX,[INTERNATVARS.Date_tim_format]
565 OR AX,AX
566 JZ USPDAT
567 DEC AX
568 JZ EUPDAT
569 CALL P_YR
570 CALL P_DSEP
571 CALL P_MON
572 CALL P_DSEP
573 MOV CX,1000H ;Do not supress leading zeroes
574 CALL P_DAY
575 JMP P_TIME
576
577USPDAT:
578 CALL P_MONTH_NAM
579 MOV CX,1110H ;Supress at most 1 leading 0
580 CALL P_DAY
581 PUSH DX
582 MOV DL,','
583 CALL PRTCHR
584 MOV DL,' '
585 CALL PRTCHR
586 POP DX
587PYA:
588 CALL P_YR
589 JMP P_TIME
590
591EUPDAT:
592 MOV CX,1110H ;Supress at most 1 leading 0
593 CALL P_DAY
594 PUSH DX
595 MOV DL,' '
596 CALL PRTCHR
597 POP DX
598 CALL P_MONTH_NAM
599 JMP PYA
600
601P_DSEP:
602 PUSH DX
603 MOV DL,[INTERNATVARS.Date_sep]
604 CALL PRTCHR
605 POP DX
606 RET
607
608P_MONTH_NAM:
609 MOV AX,DX
610 PUSH DX
611 MOV CL,5
612 SHR AX,CL
613 AND AX,0FH ;Month in AX
614 DEC AX ;Make 0 indexed
615 MOV CX,AX
616 SHL AX,1
617 ADD AX,CX ;Mult by 3 chars/mo
618 MOV SI,OFFSET DG:MONTAB
619 ADD SI,AX
620 LODSB
621 MOV DL,AL
622 CALL PRTCHR
623 LODSB
624 MOV DL,AL
625 CALL PRTCHR
626 LODSB
627 MOV DL,AL
628 CALL PRTCHR
629 MOV DL,' '
630 CALL PRTCHR
631 POP DX
632 RET
633
634P_MON:
635 MOV SI,DX
636 PUSH DX
637 MOV CL,5
638 SHR SI,CL
639 AND SI,0FH ;Month in SI
640 CALL CONVERT
641 MOV DL,AL
642 MOV CX,1000H ;Do not supress leading 0
643 CALL OUTBYTE ;Print month
644 POP DX
645 RET
646
647P_DAY:
648 MOV SI,DX
649 PUSH DX
650 PUSH CX
651 AND SI,01FH ;SI has day
652 CALL CONVERT
653 POP CX
654 MOV DL,AL
655 CALL OUTBYTE ;Print day
656 POP DX
657 RET
658
659P_YR:
660 MOV SI,DX
661 PUSH DX
662 MOV CL,9
663 SHR SI,CL
664 AND SI,07FH ;SI has raw year
665 ADD SI,1980 ;Real year
666 CALL CONVERT
667 MOV CX,1000H ;Do not supress leading zeros
668 CALL OUTWORD ;Print year
669 POP DX
670 RET
671
672P_TIME:
673 MOV DL,' '
674 CALL PRTCHR
675 POP SI
676 ADD SI,-4
677 LODSW ;Get time
678 MOV DI,AX
679 MOV SI,DI
680 MOV CL,11
681 SHR SI,CL
682 AND SI,01FH ;SI has hour
683 CMP [INTERNATVARS.Time_24],0
684 JNZ ISOK2 ;24 hour time?
685 CMP SI,12
686 JB ISOK ;Is AM
687 MOV [TCHAR],'p'
688 JZ ISOK ;Is 12-1p
689 SUB SI,12 ;Is PM
690ISOK:
691 OR SI,SI
692 JNZ ISOK2
693 MOV SI,12 ;0 is 12a
694ISOK2:
695 CALL CONVERT
696 MOV CX,1110H ;Supress at most 1 leading 0
697 MOV DL,AL
698 CALL OUTBYTE ;Print hour
699 MOV DL,BYTE PTR [INTERNATVARS.Time_sep]
700 CALL PRTCHR
701 MOV SI,DI
702 MOV CL,5
703 SHR SI,CL
704 AND SI,03FH ;SI has minute
705 CALL CONVERT
706 MOV CX,1000H ;Do not supress leading zeroes
707 MOV DL,AL
708 CALL OUTBYTE ;Print minute
709 MOV DL,[TCHAR]
710 CMP [INTERNATVARS.Time_24],0
711 JNZ NOAP ;24 hour time, no a or p
712 CALL PRTCHR ;Print a or p
713NOAP:
714 MOV DX,OFFSET DG:IDPOST
715 CALL PRINT
716 MOV [DISPFLG],0
717 RET
718
719CONVERT:
720 MOV CX,16
721 XOR AX,AX
722CNVLOOP:
723 SHL SI,1
724 CALL CONVWRD
725 CLC
726 LOOP CNVLOOP
727 RET
728
729SUBTTL Misc Routines - Mostly I/O
730PAGE
731CONVWRD:
732 ADC AL,AL
733 DAA
734 XCHG AL,AH
735 ADC AL,AL
736 DAA
737 XCHG AL,AH
738RET1: RET
739
740UNSCALE:
741 SHR CX,1
742 JC RET1
743 SHL SI,1
744 RCL DI,1
745 JMP SHORT UNSCALE
746
747DISP16BITS:
748 MOV BYTE PTR DISPFLG,1
749 JMP SHORT DISP32BITS
750
751DISPCLUS:
752 MUL [SSIZE]
753 MOV CL,[CSIZE]
754 XOR CH,CH
755 MOV SI,AX
756 MOV DI,DX
757 CALL UNSCALE
758
759DISP32BITS:
760 PUSH BP
761 PUSH BX
762 XOR AX,AX
763 MOV BX,AX
764 MOV BP,AX
765 MOV CX,32
766CONVLP:
767 SHL SI,1
768 RCL DI,1
769 XCHG AX,BP
770 CALL CONVWRD
771 XCHG AX,BP
772 XCHG AX,BX
773 CALL CONVWRD
774 XCHG AX,BX
775 ADC AL,0
776 LOOP CONVLP
777 ; Conversion complete
778 MOV CX,1310H ;Print 3-digit number with 2 leading blanks
779 CMP BYTE PTR DISPFLG,0
780 JNZ FOURDIG
781 MOV CX,1810H ;Print 8-digit number with 2 leading blanks
782 XCHG DX,AX
783 CALL DIGIT
784 XCHG AX,BX
785 CALL OUTWORD
786FOURDIG:
787 MOV AX,BP
788 CALL OUTWORD
789 MOV BYTE PTR DISPFLG,0
790 POP DX
791 CALL PRINT
792 POP BP
793 RET
794
795OUTWORD:
796 PUSH AX
797 MOV DL,AH
798 CALL OUTBYTE
799 POP DX
800OUTBYTE:
801 MOV DH,DL
802 SHR DL,1
803 SHR DL,1
804 SHR DL,1
805 SHR DL,1
806 CALL DIGIT
807 MOV DL,DH
808DIGIT:
809 AND DL,0FH
810 JZ BLANKZER
811 MOV CL,0
812BLANKZER:
813 DEC CH
814 AND CL,CH
815 OR DL,30H
816 SUB DL,CL
817 CMP BYTE PTR DISPFLG,0
818 JZ PRTCHR
819 CMP DL,30H
820 JL RET2
821PRTCHR:
822 MOV AH,STD_CON_OUTPUT
823 INT 21H
824RET2: RET
825
826PRINTCNT:
827 LODSB
828 MOV DL,AL
829 INT 21H
830 LOOP PRINTCNT
831 RET
832
833EPRINT:
834 CALL CHECKERR
835 JNZ RET$1
836 JMP SHORT PRINT
837
838DOCRLF:
839 MOV DX,OFFSET DG:CRLF
840PRINT:
841 MOV AH,STD_CON_STRING_OUTPUT
842 INT 21H
843RET$1: RET
844
845DOTCOMBMES:
846 CMP [NOISY],0
847 JZ SUBERRP
848 PUSH DX
849 CALL PRINTCURRDIRERR
850 MOV DX,OFFSET DG:CENTRY
851 CALL EPRINT
852 POP DX
853 CALL EPRINT
854 CALL DOCRLF
855 RET
856
857SUBERRP:
858 MOV AL,1
859 XCHG AL,[ERRSUB]
860 CMP AL,0
861 JNZ RET32
862 MOV SI,OFFSET DG:NUL
863 CALL PRINTCURRDIRERR
864 MOV DX,OFFSET DG:BADSUBDIR
865 CALL EPRINT
866RET32: RET
867
868
869FCB_TO_ASCZ: ;Convert DS:SI to ASCIIZ ES:DI
870 MOV CX,8
871MAINNAME:
872 LODSB
873 CMP AL,' '
874 JZ SKIPSPC
875 STOSB
876SKIPSPC:
877 LOOP MAINNAME
878 LODSB
879 CMP AL,' '
880 JZ GOTNAME
881 MOV AH,AL
882 MOV AL,'.'
883 STOSB
884 XCHG AL,AH
885 STOSB
886 MOV CL,2
887EXTNAME:
888 LODSB
889 CMP AL,' '
890 JZ GOTNAME
891 STOSB
892 LOOP EXTNAME
893
894GOTNAME:
895 XOR AL,AL
896 STOSB
897 RET
898
899CODE ENDS
900 END CHKDSK
901