;BuildCPC equ 1	; Build for Amstrad CPC on WinApe

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
	
	ifdef vasm
		include "\SrcALL\VasmBuildCompat.asm"	;Vasm <> Winape Compat
	else
		read "\SrcALL\WinApeBuildCompat.asm"	;Vasm <> Winape Compat
	endif
	
	read "QuickHeader.asm"
	
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;
;			Start Your Program Here
;
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

	LD HL,0
	LD DE,0
	LD BC,0
	LD A,0
	
	;jp Immediate			;Fixed values inline in the code
	;jp Register			;Register is the source
	;jp Extended			;16 bit Address is a source
	;jp Relative			;Jump relative to running line
	;jp RegisterIndirect	;value in a register as the address
	;jp Indexed				;IX/IY +- Offset 

	;jp Implied				;No destination needs to be specified
	
	jp BitAddressing		;Alter and read bits of registers

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;Immediate Addressing
;A fixed number parameter is specified as a parameter after the Opcode.

Immediate:
	call ShowAHLBC			;Show Registers

	ld a,-10				;Load A with immediate -10 (&F6)
	
	ld hl,16383				;Load HL width immediate 16383 (&3FFF)
	
	ld BC,&ABCD				;Load BC with immediate &ABCD
	
	ld d,%11110000			;Load D with &F0
	ld e,&69				;Load E with &69
	
	call ShowAHLBC			;Show Registers
	
	jp Finish
	
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;Register Addressing
;This is simply where the source or destination parameter is a register.

Register:	
	ld a,&69
	ld hl,&0666
	
	call ShowAHLBC			;Show Registers
	call NewLines
	
;DE=HL
	ld d,h			
	ld e,l
							
;Swap H & L
	ld a,l					;A=L
	ld l,h					;L=H
	ld h,a					;H=A
		
	call ShowAHLBC			;Show Registers
	
	jp Finish
	
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;Extended Addressing
;A 16 bit address used as a destination, either for a jump, 
; or for the address to load or store a parameter.
;The parameter will be specified in brackets (##) 
; to show the value is not an immediate.

Extended:
	call NewLine
	
	ld hl,&C000				;Address to dump
	ld c,16					;Bytes to dump
	call Monitor_MemDumpDirect
	call NewLine

	call ShowAHLBC			;Show Registers
	call NewLine
	
	
	ld a,&69
	ld (&C000),a			;Load A to address &C000
	
	ld a,&77
	ld (&C001),a			;Load A to address &C001
	
	ld bc,(&C000)			;Load BC from address &C000
	

	call ShowAHLBC			;Show Registers
	call NewLine
	
	ld hl,&C000				;Address to dump
	ld c,16					;Bytes to dump
	call Monitor_MemDumpDirect

	jp Finish
	
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;Relative Addressing
;Relative addressing is where the parameter is an 8 bit signed 
; byte offset (-128 to +127) relative to the current Program Counter 
; position (the position AFTER the JR command)

Skip2:
	ld a,'B'
	call Printchar

	jr Skip3			;Jump Relative to Skip2 (JR 14)

	
Relative:
	
	ld a,'A'
	call Printchar
	
	jr Skip1			;Jump Relative to Skip1 (JR 5)
							
	
		ld a,'1'		;This never happens!
		call Printchar
Skip1:

	jr Skip2			;Jump Relative to Skip2 (JR -21)

Skip3:
	ld a,'C'
	call Printchar
	
;Jump Relative can only jump -128 to +127
;JR won't work, but JP can jump anywhere!

	;jr LongJump			;This won't work
	;jp LongJump			;This will work
	
		ds 128			;128 Bytes of zeros
LongJump:
	
	jp Finish


;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;Register Indirect Addressing
;This is where a 16 bit register pair is specified, but the address 
; in that register is the source of the parameter, not the value in 
; the register itself. The register will be specified in brackets.

RegisterIndirect:
	call NewLine
	
	ld hl,TestRam			;Address to dump
	ld c,16					;Bytes to dump
	call Monitor_MemDumpDirect
	call NewLine

	
	ld hl,TestRam
	ld de,&0666
	
	call ShowAHLBC			;Show Registers
	call NewLine
	
	ld (hl),l				;Store L at address HL
	inc hl
	ld (hl),h				;Store H at address HL
	inc hl
	ld (hl),e				;Store E at address HL
	inc hl
	ld (hl),d				;Store D at address HL
	inc hl
	
	ld bc,TestRam
	ld a,(bc)		;Can also use (BC) (DE) but only with A
	
	call ShowAHLBC			;Show Registers
	call NewLine
	
	ld hl,TestRam			;Address to dump
	ld c,16					;Bytes to dump
	call Monitor_MemDumpDirect
	call NewLine

	ld hl,TestRam+1
	ld a,(hl)				;Load A from HL
	inc hl
	ld c,(hl)				;Load C from HL
	inc hl
	ld b,(hl)				;Load B from HL
	
	call ShowAHLBC			;Show Registers
	
	call newline
	
	ld a,&F0
	
	call ShowAHLBC			;Show Registers
	
	add (HL)				;Add the value at address HL
	
	call ShowAHLBC			;Show Registers
	call newline
	
		
	ld a,'<'			
	call PrintChar	
		
	ld hl,JumpTest
	jp (hl)					;Jump to address in HL
	
		ld a,'!'			;This never happens
		call PrintChar
	
JumpTest:
	ld a,'>'			
	call PrintChar	
	
	jp Finish

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;Indexed Addressing
;One of the two index registers (IX or IY) plus a displacement
; offset are specified.
;The displacement is an 8 bit byte, so has the possible 
; range -128 to +127.
	
Indexed:
	ld hl,TestRam			;Address to dump
	ld c,16					;Bytes to dump
	call Monitor_MemDumpDirect
	call NewLine

	ld ix,TestRam
	ld iy,TestRam+8
	
	call ShowAHLIX			;Show Registers
	call NewLines
	
	ld a,&69
	ld bc,&1234
	
;IX/IY -128 to +127 can be used as a source or destination
;IX/IY are unchanged!
	
	ld (ix+0),a				;Load address in IX+0 with A
	ld (ix+1),c				;Load address in IX+1 with C
	ld (ix+2),b				;Load address in IX+2 with B
	

	inc (iy-1)				;These can be used with more than LD!
	dec (iy-2)
	
	call ShowAHLIX			;Show Registers
	call NewLines
	
	ld hl,TestRam			;Address to dump
	ld c,16					;Bytes to dump
	call Monitor_MemDumpDirect
	
	call NewLines
	
;16 bit IX is made up if IXH and IXL
;16 bit IY is made up if IYH and IYL

	ld ixl,&69
	
	ld ixh,&77
	
	ld a,iyh

	call ShowAHLIX			;Show Registers
	call NewLines
	

	jp Finish

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;Implied Addressing
;This is where one of the parameters is implied (usually the Accumulator).

Implied:
	ld a,3
	
	call ShowAF
	
	neg					;Negate Accumulator
	call ShowAF
	neg					;Negate Accumulator
	call ShowAF
	neg					;Negate Accumulator
	call ShowAF
	
	call NewLines
	call NewLines

	ld a,&7E
	
	call ShowAF
	
	ccf					;Complement carry flag
	call ShowAF
	ccf					;Complement carry flag
	call ShowAF
	ccf					;Complement carry flag
	call ShowAF
	
	call NewLines
	
	jp Finish

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;Bit Addressing
;This is where a single bit of a register is being read or altered in a register.

BitAddressing:
	ld a,&F0
	ld bc,&00FF
	
	call ShowAHLBC			;Show Registers
	call NewLines
	call NewLines
	
	set 0,a					;Set bit 0 of A to 1
	
	set 1,b					;Set bit 1 of A to 1
	
	call ShowAHLBC			;Show Registers
	call NewLines
	call NewLines
	
	res 0,c					;Reset bit 0 of C to 0
	
	res 7,a					;Reset bit 7 of A to 0
	
	call ShowAHLBC			;Show Registers
	call NewLines
	call NewLines
	
	res 0,a					;Reset bit 0 of A to 0
	
	res 1,b					;Reset bit 0 of B to 0
	
	call ShowAHLBC			;Show Registers
	
	jp Finish
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;


Finish:
	di
	halt					;Lock the CPU

NewLines:
	push af
		call NewLine
	pop af
	ret
	

ShowAF:
	push af
	push hl
	push bc
		push af
		
		
			ld l,a
			ld a,'A'
			call ShowHexOne
			
			ld a,'F'
			call PrintChar
			ld a,':'
			call PrintChar
			
		pop af
		push af
			ld a,'C'
			jr c,ShowAF_C
			ld a,'-'
ShowAF_C:			
			call PrintChar
		pop af
		push af
			ld a,'V'
			jp pe,ShowAF_V
			ld a,'-'
ShowAF_V:	
			call PrintChar
		pop af
		push af
			ld a,'Z'
			jp pe,ShowAF_Z
			ld a,'-'
ShowAF_Z:	
			call PrintChar
		pop af
		push af
			ld a,'S'
			jp m,ShowAF_S
			ld a,'-'
ShowAF_S:	
			call PrintChar
		pop af
		
		call NewLine
	pop bc
	pop hl
	pop af
	ret	
	

ShowAHLIX:
	push af
	push hl
	push bc
		push bc
			ld l,a
			ld a,'A'
			call ShowHexOne
		pop hl
		
		ld bc,'CB'
		call ShowHexPair
		
		ld bc,'XI'
		ld a,IXL
		ld l,a
		ld a,IXH
		ld h,a
		call ShowHexPair
		
		ld bc,'YI'
		ld a,IYL
		ld l,a
		ld a,IYH
		ld h,a
		call ShowHexPair
			
		call NewLine
	pop bc
	pop hl
	pop af
	ret

ShowAHLBC:
	push af
	push hl
	push bc
		push hl
			ld l,a
			ld a,'A'
			call ShowHexOne
		
			ld h,b
			ld l,c
			ld bc,'CB'
		
			call ShowHexPair
		
			ifndef BuildGBx			;Can't Show this on the GameBoy
				ld bc,'ED'
				ld h,d
				ld l,e
				call ShowHexPair
			endif
		pop hl
		ld bc,'LH'
		call ShowHexPair
			
		call NewLine
	pop bc
	pop hl
	pop af
	ret

ShowHexOne:		;A:L
	call Printchar
	ld a,':'
	call Printchar
	jr ShowHexOneB
	
ShowHexPair:	;BC:HL
	ld a,b
	call Printchar
	ld a,c
	call Printchar
	ld a,':'
	call Printchar
	ld a,h
	call ShowHex
ShowHexOneB:
	ld a,L
	call ShowHex
	ld a,' '
	call Printchar
	ret

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;
;			End of Your program
;
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

	read "QuickFooter.asm"