		IFND	SNOOPDEBUG_I
SNOOPYDEBUG_I	EQU	1

;--------------	this is a very large macro that is called twice to read in the
;--------------	registers. It is as large as it is because it has to deal with
;--------------	register indirect stuff, which looks rather strange -> but it works!
SAVEREGS	MACRO	;\1=target,\2=MODE
		move.l	D0,\1+sregs_D0(a6)
		move.l	D1,\1+sregs_D1(a6)
		move.l	D2,\1+sregs_D2(a6)
		move.l	D3,\1+sregs_D3(a6)
		move.l	D4,\1+sregs_D4(a6)
		move.l	D5,\1+sregs_D5(a6)
		move.l	D6,\1+sregs_D6(a6)
		move.l	D7,\1+sregs_D7(a6)
		move.l	A0,\1+sregs_A0(a6)
		move.l	A1,\1+sregs_A1(a6)
		move.l	A2,\1+sregs_A2(a6)
		move.l	A3,\1+sregs_A3(a6)
		move.l	A4,\1+sregs_A4(a6)
		move.l	A5,\1+sregs_A5(a6)

		move.l	4(sp),\1+sregs_A6(a6)
		move.l	sp,\1+sregs_A7(a6)
		addq.l	#8,\1+sregs_A7(a6)

;--------------	NEW: to no longer cause enforcer-hits I test the memory via 
;--------------	exec/TypeOfMem(); this takes (considerably) longer but hey
;--------------	you asked for it!
		movem.l	d0-d7/a0-a6,-(sp)
		movea.l	a6,a5
		movea.l	4.w,a6
		movea.l	\1+sregs_A0(a5),a1
		bsr.s	.READINDIRECT
		move.l	d0,\1+sregs_I0(a5)
		movea.l	\1+sregs_A1(a5),a1
		bsr.s	.READINDIRECT
		move.l	d0,\1+sregs_I1(a5)
		movea.l	\1+sregs_A2(a5),a1
		bsr.s	.READINDIRECT
		move.l	d0,\1+sregs_I2(a5)
		movea.l	\1+sregs_A3(a5),a1
		bsr.s	.READINDIRECT
		move.l	d0,\1+sregs_I3(a5)
		movea.l	\1+sregs_A4(a5),a1
		bsr.s	.READINDIRECT
		move.l	d0,\1+sregs_I4(a5)
		movea.l	\1+sregs_A5(a5),a1
		bsr.s	.READINDIRECT
		move.l	d0,\1+sregs_I5(a5)
		bra.s	.DONEREADING

.READINDIRECT	move.l	a1,-(sp)
		jsr	-534(a6)	; TypeOfMem()
		movea.l	(sp)+,a1
		tst.l	d0
		beq.s	.SKIPREADING
		move.l	a1,d0
		bclr	#0,d0
		movea.l	d0,a1
		move.l	(a1),d0
.SKIPREADING	rts

.DONEREADING	movem.l	(sp)+,d0-d7/a0-a6
		move.l	a0,-(sp)
		movea.l	8(sp),a0
		move.l	(a0),\1+sregs_I6(a6)
		movea.l	(sp)+,a0
		move.l	8(sp),\1+sregs_I7(a6)
		ENDM

;--------------	the register structure
		STRUCTURE SnoopyRegisters,0
		ULONG	sregs_D0
		ULONG	sregs_D1
		ULONG	sregs_D2
		ULONG	sregs_D3
		ULONG	sregs_D4
		ULONG	sregs_D5
		ULONG	sregs_D6
		ULONG	sregs_D7
		ULONG	sregs_A0
		ULONG	sregs_A1
		ULONG	sregs_A2
		ULONG	sregs_A3
		ULONG	sregs_A4
		ULONG	sregs_A5
		ULONG	sregs_A6
		ULONG	sregs_A7
		ULONG	sregs_I0
		ULONG	sregs_I1
		ULONG	sregs_I2
		ULONG	sregs_I3
		ULONG	sregs_I4
		ULONG	sregs_I5
		ULONG	sregs_I6
		ULONG	sregs_I7
		LABEL	sregs_SIZEOF

;--------------	this is the message sent by SnoopyDebug()
		STRUCTURE SnoopyUserMessage,20 ; MN_SIZE
		WORD	sumsg_Type
		APTR	sumsg_Task
		APTR	sumsg_Template
		STRUCT	sumsg_RegsBeforeCall,sregs_SIZEOF
		STRUCT	sumsg_RegsAfterCall,sregs_SIZEOF
		LABEL	sumsg_SIZEOF

;--------------	this bit must be set in sumsg_Type, else Snoopy is likely to crash
		BITDEF	MSGTYPE,DEBUG,4

;--------------	this is the main macro. It is called like this :
;--------------	
;--------------		SNOOPY <function>,<template>
;--------------	
;--------------	[if <template> is #0, all registers will be shown]. Example :
;--------------	
;--------------		SNOOPY #Test,#0
;--------------		SNOOPY #Test,#TestTemplate
SNOOPY		MACRO
		move.l	\2,-(sp)
		move.l	\1,-(sp)
		jsr	SnoopyDebug
		ENDM


;--------------	additional flags
		BITDEF	REG,RESULT,6	; return value
		BITDEF	REG,BOOLEAN,7	; boolean style output
		BITDEF	REG,BYTE,8	; size = byte
		BITDEF	REG,WORD,9	; size = word
		BITDEF	REG,LONG,10	; size = long

;--------------	the register values
REGISTER_D0	equ	%001000
REGISTER_D1	equ	%001001
REGISTER_D2	equ	%001010
REGISTER_D3	equ	%001011
REGISTER_D4	equ	%001100
REGISTER_D5	equ	%001101
REGISTER_D6	equ	%001110
REGISTER_D7	equ	%001111
REGISTER_A0	equ	%010000
REGISTER_A1	equ	%010001
REGISTER_A2	equ	%010010
REGISTER_A3	equ	%010011
REGISTER_A4	equ	%010100
REGISTER_A5	equ	%010101
REGISTER_A6	equ	%010110
REGISTER_A7	equ	%010111
REGISTER_I0	equ	%100000
REGISTER_I1	equ	%100001
REGISTER_I2	equ	%100010
REGISTER_I3	equ	%100011
REGISTER_I4	equ	%100100
REGISTER_I5	equ	%100101
REGISTER_I6	equ	%100110
REGISTER_I7	equ	%100111
REGISTER_DONE	equ	-1

		ENDC	;SNOOPYDEBUG_I
;--------------	
