/*
* File:   FlexLEDdisplay.s
* Author: Howard Kelsey
*
* Created on 13th Apr 2019
*/
    .include "p33EV256GM102.inc"

    config __FSEC,	BWRP_OFF & BSS_DISABLED & BSS2_OFF & GWRP_OFF & GSS_DISABLED & CWRP_OFF & CSS_DISABLED & AIVTDIS_DISABLE
    config __FOSCSEL,	FNOSC_FRCPLL & IESO_OFF
    config __FOSC,	PLLKEN_ON & FCKSM_CSECMD & IOL1WAY_OFF & OSCIOFNC_ON & POSCMD_NONE
    config __FWDT,	WDTWIN_WIN75 & FWDTEN_OFF & WINDIS_OFF & WDTPRE_PR128 & WDTPOST_PS32768
    config __FPOR,	BOREN0_OFF
    config __FICD,	ICS_PGD1
    config __FDMT,	DMTEN_DISABLE
    
    .equ code0HighDelay, 5
    .equ code0LowDelay, 13
    .equ code1HighDelay, 10
    .equ code1LowDelay, 7
    .equ matrixMaxY, 7
    .equ matrixWidth, 32
    .equ matrixHeight, 8
    .equ matrixNoLeds, 256
    .equ kitt_fade, 10
    .equ kittMaxCount, 10
    .equ kittBrightness, 100
    .equ kittRightDir, 0
    .equ kittLeftDir, 1
    .equ kittMaxX, 32
    .equ kittAnimateDelay, 2
    .equ monsterPinkXoffset, 20
    .equ monsterCyanXoffset, 40
    .equ monsterOrangeXoffset, 60
    .equ monsterXstart, 40
    .equ monsterYstart, 1
    .equ monsterYdirUp, 0
    .equ monsterYdirDown, 1
    .equ monsterMinY, 0xFFFB
    .equ monsterMaxY, 1
    .equ monsterMinX, 0xFFF0-monsterOrangeXoffset
    .equ monsterPillsRelX, 10
    .equ monsterRed, 0
    .equ monsterPink, 1
    .equ monsterCyan, 2
    .equ monsterOrange, 3
    .equ monsterPillsXgap, 6
    .equ monsterPillsStartX, 29
    .equ monsterPillsYpos, 3
    .equ monsterPillsFurthestX, 60
    .equ monsterAnimationDelay, 20
    .equ coloursMaxCount, 20
    .equ pacmanMaxX, 33
    .equ pacmanXstart, 0xFFFB
    .equ pacmanHeight, 8
    .equ pacmanWidth, 8
    .equ pacmanAnimateDelay, 20
    .equ eyeStartXpos, 0
    .equ eyeStartYpos, 2
    .equ eyeMinXpos, 0
    .equ eyeMaxXpos, 8
    .equ eyeStartDir, 1
    .equ eyeStartCount, 0
    .equ eyeMaxCount, 5
    .equ eyeMoveDelay, 1
    .equ eyeXgap, 16
    .equ eyeLeftPauseDelay, 400
    .equ eyeRightPauseDelay, 600
    .equ eyeMoveLeft, 0
    .equ eyeMoveRight, 1
    .equ endOfRow, 0
    .equ endOfSprite, 0xFF
    .equ ascii_space, 0x20
    .equ ascii_b, 0x62  ;black
    .equ ascii_c, 0x63  ;cyan
    .equ ascii_d, 0x64  ;grey
    .equ ascii_o, 0x6F  ;orange
    .equ ascii_p, 0x70  ;pink
    .equ ascii_r, 0x72  ;red
    .equ ascii_s, 0x73  ;skin
    .equ ascii_w, 0x77  ;white
    .equ ascii_y, 0x79  ;yellow
    
;Global Declarations:
    .global __reset

;Uninitialized variables in X-space in data memory   
.section .xbss, bss, xmemory
animationStep:	   .space 2
kittXpos:	   .space 2
kittDir:	   .space 2
kittCount:	   .space 2
pacmanFrame:	   .space 2
pacmanXpos:	   .space 2
monsterXpos:	   .space 2
monsterYpos:	   .space 2
monsterYdir:	   .space 2
monsterColour:	   .space 2
eyeXpos:	   .space 2
eyeYpos:	   .space 2
eyeDir:		   .space 2
eyeCount:          .space 2
frameDelay:	   .space 2
redBuffer:         .space 256
greenBuffer:       .space 256
blueBuffer:        .space 256
	
	   
	   
;Program space initialised data

.section .const, psv
.align 2
	     
    .text
__reset:
    MOV     #__SP_init, W15
    MOV     #__SPLIM_init, W0
    MOV     W0, SPLIM
    NOP
    
    RCALL   _config_oscillator
    BCLR    TRISB, #TRISB5
    CLR	    ANSELA
    BCLR    TRISA, #TRISA4
    BCLR    LATA, #LATA4
    
    RCALL   _clear_image
    RCALL   _res

; initialise variables
    MOV	    #0, W0
    MOV	    W0, animationStep
    MOV	    #0, W0
    MOV	    W0, kittCount
    MOV	    #14, W0
    MOV	    W0, kittXpos
    MOV	    #kittRightDir, W0
    MOV	    W0, kittDir
    MOV	    W0, pacmanFrame
    MOV	    #pacmanXstart, W0
    MOV	    W0, pacmanXpos
    MOV	    #monsterXstart, W0
    MOV	    W0, monsterXpos
    MOV	    #monsterYstart, W0
    MOV	    W0, monsterYpos
    MOV	    #monsterYdirUp, W0
    MOV	    W0, monsterYdir
    MOV	    #eyeStartXpos, W0
    MOV	    W0, eyeXpos
    MOV	    #eyeStartYpos, W0
    MOV	    W0, eyeYpos
    MOV	    #eyeStartDir, W0
    MOV	    W0, eyeDir
    MOV	    #eyeStartCount, W0
    MOV	    W0, eyeCount
    MOV	    #1, W0
    MOV	    W0, frameDelay   
    
    
;    BSET    LATA, #LATA4
    
_main_loop:
    RCALL   _send_image
    RCALL   _animate_delay
    MOV	    animationStep, W0
    CP	    W0, #0
    BRA	    NZ, _main_loop_not_step0
    RCALL   _animate_monsters
    BRA	    _main_loop
_main_loop_not_step0:
    CP	    W0, #1
    BRA	    NZ, _main_loop_not_step1
    RCALL   _animate_pacman
    BRA	    _main_loop
_main_loop_not_step1:
    CP	    W0, #2
    BRA	    NZ, _main_loop_not_step2
    RCALL   _animate_kitt
    BRA	    _main_loop
_main_loop_not_step2:
    CP	    W0, #3
    BRA	    NZ, _main_loop_not_step3
    RCALL   _animate_eye
    BRA	    _main_loop  
_main_loop_not_step3:
    MOV	    #0, W0
    MOV	    W0, animationStep
    BRA     _main_loop
    
_animate_eye:
    MOV	    #eyeMoveDelay, W0
    MOV	    W0, frameDelay
    MOV	    eyeDir, W0
    CP	    W0, #eyeMoveLeft
    BRA	    NZ, _animate_eye_move_right
    DEC	    eyeXpos
    MOV	    eyeXpos, W0
    CP	    W0, #eyeMinXpos
    BRA	    NZ, _animate_eye_draw
    MOV	    #eyeMoveRight, W0
    MOV	    W0, eyeDir
    MOV	    #eyeLeftPauseDelay, W1
    MOV	    W1, frameDelay
    BRA	    _animate_eye_draw
_animate_eye_move_right:    
    INC	    eyeXpos
    MOV	    eyeXpos, W0
    CP	    W0, #eyeMaxXpos
    BRA	    NZ, _animate_eye_draw
    MOV	    #eyeMoveLeft, W0
    MOV	    W0, eyeDir
    MOV	    #eyeRightPauseDelay, W1
    MOV	    W1, frameDelay
    INC	    eyeCount
    MOV	    eyeCount, W0
    CP	    W0, #eyeMaxCount
    BRA	    NZ, _animate_eye_draw
    MOV	    #eyeStartCount, W0
    MOV	    W0, eyeCount
    INC	    animationStep
_animate_eye_draw:    
    MOV	    #20, W12
    MOV	    #20, W13
    MOV	    #20, W14
    RCALL   _fill_image   
    MOV	    eyeXpos, W10
    MOV	    eyeYpos, W11
    MOV     #tblpage(_eye), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_eye), W1
    RCALL   _draw_sprite
    MOV	    eyeXpos, W10
    MOV	    eyeYpos, W11
    ADD	    #eyeXgap, W10
    MOV     #tblpage(_eye), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_eye), W1
    RCALL   _draw_sprite
    MOV	    #0, W10
    MOV	    #0, W11
    MOV     #tblpage(_skin), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_skin), W1
    RCALL   _draw_sprite
    RETURN       
    
_draw_monster:
    MOV	    monsterColour, W0
    CP	    W0, #monsterRed
    BRA	    NZ, _draw_monster_not_red
    MOV	    monsterXpos, W10
    MOV	    monsterYpos, W11
    MOV     #tblpage(_monsterRed), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_monsterRed), W1
_draw_monster_not_red:
    CP	    W0, #monsterPink
    BRA	    NZ, _draw_monster_not_pink
    MOV	    monsterXpos, W10
    ADD	    #monsterPinkXoffset, W10
    MOV	    monsterYpos, W11
    MOV     #tblpage(_monsterPink), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_monsterPink), W1
_draw_monster_not_pink:
    CP	    W0, #monsterCyan
    BRA	    NZ, _draw_monster_not_cyan
    MOV	    monsterXpos, W10
    ADD	    #monsterCyanXoffset, W10
    MOV	    monsterYpos, W11
    MOV     #tblpage(_monsterCyan), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_monsterCyan), W1
_draw_monster_not_cyan:
    CP	    W0, #monsterOrange
    BRA	    NZ, _draw_monster_not_orange
    MOV	    monsterXpos, W10
    ADD	    #monsterOrangeXoffset, W10
    MOV	    monsterYpos, W11
    MOV     #tblpage(_monsterOrange), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_monsterOrange), W1
_draw_monster_not_orange:
    RCALL   _draw_sprite
    RETURN
    
    
_animate_monsters:
    RCALL   _clear_image
    RCALL   _monster_pills
    MOV	    #monsterRed, W0
    MOV	    W0, monsterColour
    RCALL   _draw_monster
    MOV	    #monsterPink, W0
    MOV	    W0, monsterColour
    RCALL   _draw_monster
    MOV	    #monsterCyan, W0
    MOV	    W0, monsterColour
    RCALL   _draw_monster
    MOV	    #monsterOrange, W0
    MOV	    W0, monsterColour
    RCALL   _draw_monster    
    ; Check which direction the monster is going
    MOV	    monsterYdir, W0
    CP	    W0, #monsterYdirUp
    BRA	    Z, _animate_monster_ydir_up
    ; monster is going down.  Check if at bottom
    INC	    monsterYpos
    MOV	    monsterYpos, W0
    MOV	    #monsterMaxY, W2
    CP	    W0, W2
    BRA	    NZ, _animate_monster_ydir_skip
    MOV	    #monsterYdirUp, W0
    MOV	    W0, monsterYdir
    BRA	    _animate_monster_ydir_skip
_animate_monster_ydir_up:
    DEC	    monsterYpos
    MOV	    monsterYpos, W0
    MOV	    #monsterMinY, W2
    CP	    W0, W2
    BRA	    NZ, _animate_monster_ydir_skip
    MOV	    #monsterYdirDown, W0
    MOV	    W0, monsterYdir
_animate_monster_ydir_skip:
    DEC	    monsterXpos
    MOV	    monsterXpos, W0
    MOV	    #monsterMinX, W2
    CP	    W0, W2
    BRA	    NZ, _animate_monster_end
    MOV	    #monsterXstart, W0
    MOV	    W0, monsterXpos
    MOV	    #monsterYstart, W0
    MOV	    W0, monsterYpos
    MOV	    #monsterYdirUp, W0
    MOV	    W0, monsterYdir
    INC	    animationStep
_animate_monster_end:
    MOV	    #monsterAnimationDelay, W0
    MOV	    W0, frameDelay
    RETURN    

_monster_pills:
    MOV	    #monsterPillsStartX, W10
    MOV	    #0, W12
    MOV	    #4, W13
    MOV	    #0, W14
_monster_pills_loop:
    MOV	    monsterXpos, W7
    ADD	    #monsterPillsFurthestX, W7
    ADD	    #monsterPillsRelX, W7
    CP	    W10, W7
    BRA	    N, _monster_pills_exit
    MOV	    #monsterPillsYpos, W11
    RCALL   _plot
    INC	    W11, W11
    RCALL   _plot
    INC	    W10, W10
    RCALL   _plot
    DEC	    W11, W11
    RCALL   _plot
    SUB	    #monsterPillsXgap, W10
    BRA	    _monster_pills_loop
_monster_pills_exit:
    RETURN     

_animate_pacman:
    RCALL   _clear_image
    RCALL   _pacman_pills
    MOV	    pacmanFrame, W0
    CP	    W0, #0
    BRA	    NZ, _pacman_not_frame_0
    MOV     #tblpage(_packman0), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_packman0), W1
_pacman_not_frame_0:
    CP	    W0, #1
    BRA	    NZ, _pacman_not_frame_1
    MOV     #tblpage(_packman1), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_packman1), W1
_pacman_not_frame_1:
    CP	    W0, #2
    BRA	    NZ, _pacman_not_frame_2
    MOV     #tblpage(_packman2), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_packman2), W1
_pacman_not_frame_2:
    CP	    W0, #3
    BRA	    NZ, _pacman_not_frame_3
    MOV     #tblpage(_packman3), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_packman3), W1
_pacman_not_frame_3:
    CP	    W0, #4
    BRA	    NZ, _pacman_not_frame_4
    MOV     #tblpage(_packman4), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_packman4), W1
_pacman_not_frame_4:
    CP	    W0, #5
    BRA	    NZ, _pacman_not_frame_5
    MOV     #tblpage(_packman3), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_packman3), W1
 _pacman_not_frame_5:
    CP	    W0, #6
    BRA	    NZ, _pacman_not_frame_6
    MOV     #tblpage(_packman2), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_packman2), W1
 _pacman_not_frame_6:
    CP	    W0, #7
    BRA	    NZ, _pacman_not_frame_7
    MOV     #tblpage(_packman1), W1
    MOV	    W1, TBLPAG
    MOV	    #tbloffset(_packman1), W1
    MOV	    #0, W0
    MOV	    W0, pacmanFrame
    BRA	    _animate_pacman_loop1
 _pacman_not_frame_7: 
    INC	    pacmanFrame
_animate_pacman_loop1:
    MOV	    pacmanXpos, W10
    MOV	    #0, W11
    RCALL   _draw_sprite
    INC	    pacmanXpos
    MOV	    pacmanXpos, W0
    CP	    W0, #pacmanMaxX
    BRA	    NZ, _animate_pacman_end
    INC	    animationStep
    MOV	    #pacmanXstart, W0
    MOV	    W0, pacmanXpos
_animate_pacman_end:
    MOV	    #pacmanAnimateDelay, W0
    MOV	    W0, frameDelay
    RETURN
    
_pacman_pills:
    MOV	    #monsterPillsStartX, W10
    MOV	    #0, W12
    MOV	    #4, W13
    MOV	    #0, W14
_pacman_pills_loop:
    MOV	    pacmanXpos, W0
    CP	    W10, W0
    BRA	    N, _pacman_pills_exit
    MOV	    #monsterPillsYpos, W11
    RCALL   _plot
    INC	    W11, W11
    RCALL   _plot
    INC	    W10, W10
    RCALL   _plot
    DEC	    W11, W11
    RCALL   _plot
    SUB	    #monsterPillsXgap, W10
    BRA	    _pacman_pills_loop
_pacman_pills_exit:
    RETURN  
    
_animate_kitt:
    MOV	    #0, W12
    MOV	    #100, W13
    MOV	    #0, W14
    MOV	    kittXpos, W10
_animate_kitt_right_loop:
    CP	    W10, #kittMaxX
    BRA	    Z, _animate_kitt_right_loop_exit    
    RCALL   _animate_kitt_vert_line
    SUB	    #kitt_fade, W13
    BRA	    NN, _animate_kit_right_not_neg
    ADD	    #kitt_fade, W13
_animate_kit_right_not_neg:
    INC	    W10, W10
    BRA	    _animate_kitt_right_loop
_animate_kitt_right_loop_exit:
    MOV	    #kittBrightness, W13
    MOV	    kittXpos, W10
_animate_kitt_left_loop:
    DEC	    W10, W10
    BRA	    N, _animate_kitt_left_loop_exit
    SUB	    #kitt_fade, W13
    BRA	    NN, _animate_kit_left_not_neg
    ADD	    #kitt_fade, W13
_animate_kit_left_not_neg:
    RCALL   _animate_kitt_vert_line
    BRA	    _animate_kitt_left_loop
_animate_kitt_left_loop_exit:
    MOV	    kittDir, W0
    CP	    W0, #kittRightDir
    BRA	    NZ, _animate_kitt_move_left
    INC	    kittXpos
    MOV	    kittXpos, W0
    CP	    W0, #kittMaxX
    BRA	    NZ, _animate_kitt_end
    MOV	    #kittLeftDir, W0
    MOV	    W0, kittDir
    BRA	    _animate_kitt_end
_animate_kitt_move_left:
    DEC	    kittXpos
    BRA	    NZ, _animate_kitt_end
    MOV	    #kittRightDir, W0
    MOV	    W0, kittDir
    INC	    kittCount
    MOV	    kittCount, W0
    CP	    W0, #kittMaxCount
    BRA	    NZ, _animate_kitt_end
    MOV	    #0, W0
    MOV	    W0, kittCount
    INC	    animationStep
_animate_kitt_end:
    MOV	    #kittAnimateDelay, W0
    MOV	    W0, frameDelay
    RETURN
    
_animate_kitt_vert_line:
    MOV	    #matrixMaxY, W11
_animate_kitt_vert_line_loop:
    RCALL   _plot
    DEC	    W11, W11
    BRA	    NN, _animate_kitt_vert_line_loop
    RETURN

_draw_sprite:
    MOV	    W10, W2
_draw_sprite_loop1:
    MOV	    W2, W10
_draw_sprite_loop2:
    TBLRDL.b  [W1++], W0
    CP	    W0, #endOfRow
    BRA	    Z, _draw_sprite_exit_loop2
    CP	    W0, #endOfSprite
    BRA	    Z, _draw_sprite_exit_loop1
    CP	    W0, #ascii_b
    BRA	    NZ, _draw_sprite_not_black
    MOV	    #0, W12
    MOV	    #0, W13
    MOV	    #0, W14
_draw_sprite_not_black:
    CP	    W0, #ascii_s
    BRA	    NZ, _draw_sprite_not_skin
    MOV	    #4, W12
    MOV	    #8, W13
    MOV	    #3, W14    
_draw_sprite_not_skin:    
    CP	    W0, #ascii_p
    BRA	    NZ, _draw_sprite_not_pink
    MOV	    #10, W12
    MOV	    #30, W13
    MOV	    #10, W14    
_draw_sprite_not_pink:       
    CP	    W0, #ascii_c
    BRA	    NZ, _draw_sprite_not_cyan
    MOV	    #5, W12
    MOV	    #5, W13
    MOV	    #40, W14
_draw_sprite_not_cyan:
    CP	    W0, #ascii_o
    BRA	    NZ, _draw_sprite_not_orange
    MOV	    #10, W12
    MOV	    #30, W13
    MOV	    #0, W14    
_draw_sprite_not_orange:  
    CP	    W0, #ascii_r
    BRA	    NZ, _draw_sprite_not_red
    MOV	    #0, W12
    MOV	    #30, W13
    MOV	    #0, W14
_draw_sprite_not_red:  
    CP	    W0, #ascii_w
    BRA	    NZ, _draw_sprite_not_white
    MOV	    #20, W12
    MOV	    #20, W13
    MOV	    #20, W14
_draw_sprite_not_white:
    CP	    W0, #ascii_y
    BRA	    NZ, _draw_sprite_not_yellow
    MOV	    #30, W12
    MOV	    #50, W13
    MOV	    #0, W14
_draw_sprite_not_yellow:
    CP	    W0, #ascii_space
    BRA	    Z, _draw_sprite_dont_plot  
    RCALL   _plot
_draw_sprite_dont_plot:    
    INC	    W10, W10
    BRA	    _draw_sprite_loop2
_draw_sprite_exit_loop2:
    INC	    W11, W11
    BRA	    _draw_sprite_loop1
_draw_sprite_exit_loop1:
    RETURN    
     
_animate_delay:
    MOV	    frameDelay, W0
    MOV	    #0, W1
_animate_delay_loop:
    DEC	    W1, W1
    BRA	    NZ, _animate_delay_loop
    DEC	    W0, W0
    BRA	    NZ, _animate_delay_loop
    RETURN
    
_plot:
    CP      W10, #matrixWidth
    BRA	    C, _plot_end
    CP      W11, #matrixHeight
    BRA	    C, _plot_end
    MOV	    W10, W9
    SL	    W9, W9
    SL	    W9, W9
    SL	    W9, W9
    BTSC    W10, #0 ;check if this is an even column
    BRA	    _plot_odd_x
    ADD	    W9, W11, W9
    BRA	    _plot_skip_odd_x
_plot_odd_x:
    ADD	    #(matrixHeight-1), W9
    SUB	    W9, W11, W9
_plot_skip_odd_x:
    MOV	    #greenBuffer, W8
    ADD	    W8, W9, W8
    MOV.b   W12, [W8]
    MOV	    #redBuffer, W8
    ADD	    W8, W9, W8
    MOV.b   W13, [W8]
    MOV	    #blueBuffer, W8
    ADD	    W8, W9, W8
    MOV.b   W14, [W8] 
_plot_end:
    RETURN
    
_send_image:
    MOV	    #matrixNoLeds, W1
    MOV	    #greenBuffer, W2
    MOV	    #redBuffer, W3
    MOV	    #blueBuffer, W4
_send_image_loop:
    MOV.B   [W2++], W5
    RCALL   _send_colour
    MOV.B   [W3++], W5
    RCALL   _send_colour
    MOV.B   [W4++], W5
    RCALL   _send_colour
    DEC	    W1, W1
    BRA	    NZ, _send_image_loop
    RCALL   _res
    RETURN
    
_send_colour:
    MOV	    #7, W6 ;Start sending bit 7
_send_colour_loop:
    BTST.Z  W5, W6
    BRA	    NZ,	_send_colour_1
    RCALL   _code0;
    BRA	    _send_colour_next
_send_colour_1:
    RCALL   _code1;
_send_colour_next:
    DEC	    W6, W6
    BRA	    NN, _send_colour_loop    
    RETURN
    
_code0:
    BSET    LATB, #LATB5
    MOV	    #code0HighDelay, W0
_code0_loop1:
    DEC	    W0, W0
    BRA	    NZ, _code0_loop1
    BCLR    LATB, #LATB5
    MOV	    #code0LowDelay, W0
_code0_loop2:
    DEC	    W0, W0
    BRA	    NZ, _code0_loop2
    RETURN
    
_code1:
    BSET    LATB, #LATB5
    MOV	    #code1HighDelay, W0
_code1_loop1:
    DEC	    W0, W0
    BRA	    NZ, _code1_loop1
    BCLR    LATB, #LATB5
    MOV	    #code1LowDelay, W0
_code1_loop2:
    DEC	    W0, W0
    BRA	    NZ, _code1_loop2
    RETURN    
    
_res:
    BCLR    LATB, #LATB5
    RETURN
    
_clear_image:
    MOV	    #0, W12
    MOV	    #0, W13
    MOV	    #0, W14
_fill_image:
    MOV	    #matrixNoLeds, W1
    MOV	    #greenBuffer, W2
    MOV	    #redBuffer, W3
    MOV	    #blueBuffer, W4  
_fill_buffer_loop:
    MOV.B   W12, [W2++]
    MOV.B   W13, [W3++]
    MOV.B   W14, [W4++]
    DEC	    W1, W1
    BRA	    NZ, _fill_buffer_loop
    RETURN

_config_oscillator:
    ;Fast RC oscillator (FRC) with PLL
    CLR     CLKDIV
    MOV     #74, W0
    MOV     W0, PLLFBDL
;Place the New Oscillator Selection (NOSC=0b001) in W0
    MOV	    #0x01, W1
;OSCCONH (high byte) Unlock Sequence
    MOV.b   OSCCONH, WREG
    AND     #0xF8, W0
    IOR     W0, W1, W0
    MOV     #OSCCONH, W1
    MOV	    #0x78, W2
    MOV	    #0x9A, W3
    MOV.B   W2, [W1] ; Write 0x0078
    MOV.B   W3, [W1] ; Write 0x009A
;Set New Oscillator Selection
    MOV.B   WREG, OSCCONH
;Place 0x01 in W0 for setting clock switch enabled bit
;OSCCONL (low byte) Unlock Sequence
    MOV	    #OSCCONL, W1
    MOV.b   #0x01, W0
    MOV	    #0x46, W2
    MOV	    #0x57, W3
    MOV.B   W2, [W1] ; Write 0x0046
    MOV.B   W3, [W1] ; Write 0x0057
; Enable Clock Switch
    MOV.B   W0, [W1] ; Request Clock Switching by Setting OSWEN bit
_config_oscillator_oswen_wait:
    BTSC    OSCCONL, #OSWEN
    BRA	    _config_oscillator_oswen_wait
;Clock switching is disabled, system clock source is locked
    BSET    OSCCONL, #CLKLOCK
;Wait for PLL to lock
_config_oscillator_lock_wait:
    BTSS    OSCCONL, #LOCK
    BRA	    _config_oscillator_lock_wait
    RETURN

_eye:
    .string "  cccc  "
    .string " cccccc "
    .string " ccbbcc "
    .string " ccbbcc "
    .string " cccccc "
    .string "  cccc  "
    .byte 0xFF
_packman0:
    .string "  yyyy  "
    .string " yyyyyy "
    .string "yyyyyyyy"
    .string "yyyyyyyy"
    .string "yyyyyyyy"
    .string "yyyyyyyy"
    .string " yyyyyy "
    .string "  yyyy  "
    .byte   0xFF
_packman1:  
    .string "  yyyy  "
    .string " yyyyyy "
    .string "yyyyyyyy"
    .string "yyyy    "
    .string "yyyyyyyy"
    .string "yyyyyyyy"
    .string " yyyyyy "
    .string "  yyyy  "
    .byte   0xFF 
_packman2:
    .string "  yyyy  "
    .string " yyyyyy "
    .string "yyyyyyyy"
    .string "yyyy    "
    .string "yyyy    "
    .string "yyyyyyyy"
    .string " yyyyyy "
    .string "  yyyy  "
    .byte   0xFF 
_packman3:
    .string "  yyyy  "
    .string " yyyyyy "
    .string "yyyyyy  "
    .string "yyyy    "
    .string "yyyy    "
    .string "yyyyyy  "
    .string " yyyyyy "
    .string "  yyyy  "
    .byte   0xFF   
 _packman4:
    .string "  yyyy  "
    .string " yyyyy  "
    .string "yyyyy   "
    .string "yyyy    "
    .string "yyyy    "
    .string "yyyyy   "
    .string " yyyyy  "
    .string "  yyyy  "
    .byte   0xFF   
_monsterRed:
    .string "     rrrr     "
    .string "   rrrrrrrr   "
    .string "  rrrrrrrrrr  "
    .string " rrrrrrrrrrrr "
    .string " rwwwwrrwwwwr "
    .string "rrbbwwrrbbwwrr"
    .string "rrwwwwrrwwwwrr"
    .string "rrrrrrrrrrrrrr"
    .string "rrrrrrrrrrrrrr"
    .string "rrrrrrrrrrrrrr"
    .string "rrrr rrrr rrrr"
    .string " rr   rr   rr "    
    .byte   0xFF
_monsterPink:
    .string "     pppp     "
    .string "   pppppppp   "
    .string "  pppppppppp  "
    .string " pppppppppppp "
    .string " pwwwwppwwwwp "
    .string "ppbbwwppbbwwpp"
    .string "ppwwwwppwwwwpp"
    .string "pppppppppppppp"
    .string "pppppppppppppp"
    .string "pppppppppppppp"
    .string "pppp pppp pppp"
    .string " pp   pp   pp "    
    .byte   0xFF       
_monsterOrange:
    .string "     oooo     "
    .string "   oooooooo   "
    .string "  oooooooooo  "
    .string " oooooooooooo "
    .string " owwwwoowwwwo "
    .string "oobbwwoobbwwoo"
    .string "oowwwwoowwwwoo"
    .string "oooooooooooooo"
    .string "oooooooooooooo"
    .string "oooooooooooooo"
    .string "oooo oooo oooo"
    .string " oo   oo   oo "    
    .byte   0xFF
_monsterCyan:
    .string "     cccc     "
    .string "   cccccccc   "
    .string "  cccccccccc  "
    .string " cccccccccccc "
    .string " cwwwwccwwwwc "
    .string "ccbbwwccbbwwcc"
    .string "ccwwwwccwwwwcc"
    .string "cccccccccccccc"
    .string "cccccccccccccc"
    .string "cccccccccccccc"
    .string "cccc cccc cccc"
    .string " cc   cc   cc "    
    .byte   0xFF
_skin:
    .string "ssssssssssssssssssssssssssssssss"
    .string "ssssss     ssssssssss     ssssss"
    .string "ssss        ssssssss        ssss"
    .string "sss          ssssss          sss"
    .string "s             ssss             s"
    .string "sss          ssssss          sss"
    .string "sssss      ssssssssss      sssss"
    .string "ssssssssssssssssssssssssssssssss"
    .byte   0xFF
    