When I was pursuing a B.Sc. degree in Loyola Academy around 1996 or 1997, we used DOS and diskless machines with floppies. There was a pretty terrible virus called Die Hard 2 doing the rounds in the labs. We didn't have a cleaner utility for this virus, and even if the McAfee SCAN.EXE and CLEAN.EXE that we had could detect and clean it (which they couldn't anyway), they were way too slow to run. Simply loading either off a floppy into memory and program setup took a minute on those 8088 machines and then scanning took what seemed to be forever. It was during this time when I was getting better at assembly and also going through virus disassembly :). I wrote a program called DH2C.COM (Die Hard 2 cleaner) in 8086 assembly which got used a lot on campus for its high speed, so much so that some people changed strings in it using a hex editor and called it their own. You could clean an entire disk in less time than SCAN.EXE took to load. This was due to DH2C's use of file truncation and very little disk reading to check for infection.
Here is the program DH2C.COM in a zip file. I seem to have lost the original source code over the years, but the following is a disassembly of it. I don't know if I can release this disassembler-generated code as free software, but the DH2C.COM file is released under the modified BSD license or GNU GPLv2 and higher (no warranty, no liability). If time permits, I will comment it in the future but it should be fairly straightforward to anyone who has done DOS programming.
The following source code can be downloaded as DH2C.ASM.
;********* File: dh2c.com *************
;
code SEGMENT
ASSUME CS:code, DS:code
ORG 100h
strt:
CLD
XOR CX,CX
MOV DX ,03C6h
CALL J0033F
CMP AL,FFh
JNZ J00116
J0010D: MOV DX ,03FDh
CALL J0033F
JMP SHORT J00170
DB 90h ;00115
J00116: CMP BYTE PTR [0080h],00h
JZ J0010D
MOV DI ,039Dh
MOV SI ,0081h
J00123: LODSB
CMP AL,0Dh
JZ J00146
CMP AL,20h
JBE J00123
CMP BYTE PTR [005Ch],00h
JZ J00139
LODSB
LODSB
CMP AL,20h
JBE J0013F
J00139: STOSB
LODSB
CMP AL,20h
JA J00139
J0013F: MOV AL,[005Ch]
OR AL,AL
JNZ J0014C
J00146: MOV AH ,19h
INT 21 ; DOS Function Call
INC AL
J0014C: ADD [034Bh],AL
MOV DX ,097Eh
SUB DX,+2Bh
MOV BX ,034Eh
CALL J00172
CMP BYTE PTR [03AAh],FFh
JNZ J00170
MOV BX ,0002h
MOV CX ,001Ah
MOV AH ,40h
MOV DX ,03ABh
INT 21 ; DOS Function Call
J00170: INT 20 ; Terminate a COM program
J00172: PUSH DX
MOV SI ,039Dh
CALL J001EF
XOR CX,CX
CALL J001CE
JB J0018A
J00180: CALL J001F8
CALL J001E3
JB J0018A
JMP J00180
J0018A: POP DX
PUSH DX
MOV SI ,0347h
CALL J001EF
MOV CX ,0010h
CALL J001CE
J00198: JB J001CC
MOV SI,DX
TEST BYTE PTR [SI+15h],10h
JNZ J001A7
J001A2: CALL J001E3
JMP J00198
J001A7: CMP BYTE PTR [SI+1Eh],2Eh
JZ J001A2
PUSH DI
PUSH BX
MOV SI,DX
ADD SI,+1Eh
CALL J001EF
MOV BX,DI
STOSB
MOV BYTE PTR [BX-01h],5Ch
CALL J00172
POP BX
POP DI
MOV BYTE PTR [BX],00h
MOV AH ,1Ah
INT 21 ; DOS Function Call
JMP J001A2
J001CC: POP DX
RETN
J001CE: PUSH CX
ADD DX,+2Ch
MOV AH ,1Ah
INT 21 ; DOS Function Call
MOV BP,DX
MOV AH ,4Eh
MOV DX ,034Bh
INT 21 ; DOS Function Call
MOV DX,BP
POP CX
RETN
J001E3: MOV BP,DX
MOV AH ,4Fh
MOV DX ,034Bh
INT 21 ; DOS Function Call
MOV DX,BP
RETN
J001EF: MOV DI,BX
J001F1: LODSB
STOSB
OR AL,AL
JNZ J001F1
RETN
J001F8: MOV BP,DX
CMP BYTE PTR [BP+1Eh],2Eh
JZ J00232
MOV DX ,034Bh
XOR AL,AL
MOV [03AAh],AL
XCHG AL,[BX]
XCHG AX,DI
MOV WORD PTR [0476h],0478h
CALL J00233
XCHG AX,DI
MOV [BX],AL
MOV DX,BP
ADD DX,+1Eh
CALL J00233
PUSH DI
PUSH AX
MOV DI,[0476h]
XOR AX,AX
STOSB
POP AX
POP DI
MOV DX ,0478h
CALL J00256
MOV DX,BP
J00232: RETN
J00233: PUSH DI
MOV DI,[0476h]
MOV SI,DX
MOV AH ,02h
LODSB
J0023D: MOV DL,AL
INT 21 ; DOS Function Call
STOSB
LODSB
OR AL,AL
JNZ J0023D
MOV [0476h],DI
POP DI
RETN
J0024D: MOV DX ,0452h
CALL J0033F
JMP J0032F
J00256: PUSH AX
PUSH BX
PUSH CX
PUSH DX
PUSH SI
PUSH DI
PUSHF
MOV AX ,3D02h
INT 21 ; DOS Function Call
MOV [0578h],AX
JB J0024D
MOV BX,AX
MOV AX ,4202h
XOR CX,CX
XOR DX,DX
INT 21 ; DOS Function Call
JB J0024D
CMP DX,+00h
JNZ J0027E
CMP AX,0FA0h
JB J002CA
J0027E: MOV [097Ah],AX
MOV [097Ch],DX
MOV AX ,4200h
XOR CX,CX
XOR DX,DX
INT 21 ; DOS Function Call
JB J0024D
MOV AH ,3Fh
MOV CX ,0200h
MOV DX ,057Ah
INT 21 ; DOS Function Call
JB J0024D
MOV BX,[0578h]
MOV AX ,4202h
MOV CX ,FFFFh
MOV DX ,0FA0h
NEG DX
INT 21 ; DOS Function Call
JB J0024D
MOV AH ,3Fh
MOV CX ,0200h
MOV DX ,077Ah
INT 21 ; DOS Function Call
JB J0024D
CMP WORD PTR [077Ah],00E8h
JNZ J002CA
CMP BYTE PTR [077Ch],00h
JZ J002D3
J002CA: MOV DX ,03C3h
CALL J0033F
JMP SHORT J0032F
DB 90h ;002D2
J002D3: MOV DX ,0423h
CALL J0033F
PUSH CS
POP ES
MOV DI ,057Ah
MOV SI ,07E0h
MOV CX ,0018h
MOV BX,SI
J002E6: NOT BYTE PTR [BX]
INC BX
LOOP J002E6
MOV CX ,0018h
REPZ MOVSB
MOV AX ,4200h
MOV BX,[0578h]
XOR CX,CX
XOR DX,DX
INT 21 ; DOS Function Call
MOV AH ,40h
MOV BX,[0578h]
MOV CX ,0200h
MOV DX ,057Ah
INT 21 ; DOS Function Call
MOV BX,[0578h]
MOV AX ,4202h
MOV CX ,FFFFh
MOV DX ,0FA0h
NEG DX
INT 21 ; DOS Function Call
MOV AH ,40h
MOV BX,[0578h]
XOR CX,CX
MOV DX ,057Ah
INT 21 ; DOS Function Call
MOV DX ,0447h
CALL J0033F
J0032F: MOV BX,[0578h]
MOV AH ,3Eh
INT 21 ; DOS Function Call
POPF
POP DI
POP SI
POP DX
POP CX
POP BX
POP AX
RETN
J0033F: PUSH AX
MOV AX ,0900h
INT 21 ; DOS Function Call
POP AX
RETN
DB "*.*" ;00347
DB 00h ;0034A
DB "@:\" ;0034B
DB 79 DUP (00h) ;0034E
DB "*.*" ;0039D
DB 10 DUP (00h) ;003A0
DB FFh ;003AA
DB "No matching files found." ;003AB
DB 0Dh ;003C3
DB 0Ah ;003C4
DB "$" ;003C5
DB 0Dh ;003C6
DB 0Ah ;003C7
DB "DieHard-II Virus Remover - By Mukund & Friend" ;003C8
DB "s" ;003F5
DB 0Dh ;003F6
DB 0Ah ;003F7
DB 0Dh ;003F8
DB 0Ah ;003F9
DB 0Dh ;003FA
DB 0Ah ;003FB
DB "$" ;003FC
DB 0Dh ;003FD
DB 0Ah ;003FE
DB "Usage : DH2C" ;003FF
DB 09h ;0040B
DB "[drive:] [wildcards]" ;0040C
DB 0Dh ;00420
DB 0Ah ;00421
DB "$ - File Infected! Removing Virus...." ;00422
DB 0Dh ;0044F
DB 0Ah ;00450
DB "$" ;00451
DB 0Dh ;00452
DB 0Ah ;00453
DB "Error accessing file. Skipping." ;00454
DB 0Dh ;00473
DB 0Ah ;00474
DB "$" ;00475
DB 257 DUP (00h) ;00476
DB 00h ;00577
code ENDS
END strt