; This ucode can copy the dsp instruction rom and coefficient table. ; irom: ; 0x8000 in instruction space ; coef: ; 0x1000 in data space ; ; Both irom and coef are 0x1000 words in length - remember, DSP ; uses 16bit words ; ; The DSP has two address spaces, to load data from instruction ; space you need to use 'i'-prefixed instructions. /********************************/ /** HANDY THANGERS **/ /********************************/ ; External MEM_BASE: equ 0x0000 MEM_HI: equ MEM_BASE MEM_LO: equ MEM_BASE+1 ; DSP DRAM_BASE: equ 0x0000 ; Config reg controls dma behavior CR_TO_DSP: equ 0 CR_TO_CPU: equ 1 CR_IRAM: equ 2 CR_DRAM: equ 0 IROM_BASE: equ 0x8000 COEF_BASE: equ 0x1000 DUMP_SIZE: equ 0x2000 ; in bytes! /**************************************************************/ /* CODE START */ /**************************************************************/ ; iram 0x00 - Exception vectors ; 8 vectors, 2 opcodes each jmp exception0 jmp exception1 jmp exception2 jmp exception3 jmp exception4 jmp exception5 jmp exception6 jmp exception7 ; iram 0x10 - Our entry point sbset #0x02 sbset #0x03 sbclr #0x04 sbset #0x05 sbset #0x06 ; ??? s16 lri $CR, #0x00ff /**************************************************************/ /* MAIN */ /**************************************************************/ ; This ucode is meant only to dump the ROMs, and as such is ; self-contained and skimpy main: clr $acc1 clr $acc0 ; This consumes ALL of dram! We must be careful until we dma it! call copy_irom_to_dram ; Send mail saying irom dump is done call wait_for_dsp_mbox si @DMBH, #0x8888 si @DMBL, #0xc0de si @DIRQ, #0x0001 ; Get address to dma to, dma, and wait till done call dma_dram_to_cmbl ; Now we can start over for the coef call copy_coef_to_dram ; Send mail saying coef dump is done call wait_for_dsp_mbox si @DMBH, #0x8888 si @DMBL, #0xda7a si @DIRQ, #0x0001 ; Get address to dma to, dma, and wait till done call dma_dram_to_cmbl ; Die do_halt: halt /**************************************************************/ /* HELPER FUNCTIONS */ /**************************************************************/ /********************************/ /** DUMPING FUNCTIONS **/ /********************************/ ; Dump irom from 0x8000 in instruction space copy_irom_to_dram: lri $ar0, #IROM_BASE lri $ar1, #DRAM_BASE lri $ar2, #DUMP_SIZE/2 ; each iteration copies a word bloop $ar2, copy_irom_to_dram_end ilrri $ac0.m, @$ar0 ; Now ac0.m is 16bits of irom! srri @$ar1, $ac0.m copy_irom_to_dram_end: nop ret ; Dump coef from 0x1000 in data space copy_coef_to_dram: lri $ar0, #COEF_BASE lri $ar1, #DRAM_BASE lri $ar2, #DUMP_SIZE/2 ; each iteration copies a word bloop $ar2, copy_coef_to_dram_end lrri $ac0.m, @$ar0 ; Now ac0.m is 16bits of coef! srri @$ar1, $ac0.m copy_coef_to_dram_end: nop ret /********************************/ /** DMA **/ /********************************/ ; DMA implementation which does not write to dram ; We take advantage of the fact that we know the mail is going to ; contain the address which we should dma to dma_dram_to_cmbl: call wait_for_cpu_mbox lrs $ac0.m, @CMBL andi $ac1.m, #0x7fff ; Directly do dma; writing the length kicks it off sr @DSMAH, $ac1.m sr @DSMAL, $ac0.m si @DSPA, #DRAM_BASE si @DSCR, #(CR_TO_CPU|CR_DRAM) si @DSBL, #DUMP_SIZE ; Waits for previous DMA to complete by watching a bit in DSCR. wait_dma: lrs $ac1.m, @DSCR andcf $ac1.m, #0x0004 jlz wait_dma ret /********************************/ /** MAILBOX **/ /********************************/ ; Waits for a mail to arrive in the DSP in-mailbox. wait_for_dsp_mbox: lrs $ac1.m, @DMBH andcf $ac1.m, #0x8000 jlz wait_for_dsp_mbox ret ; Waits for the CPU to grab a mail that we just sent from the DSP. wait_for_cpu_mbox: lrs $ac1.m, @CMBH andcf $ac1.m, #0x8000 jlnz wait_for_cpu_mbox ret /********************************/ /** EXCEPTION HANDLERS **/ /********************************/ ; ...zey do nutzing! exception0: rti exception1: rti exception2: rti exception3: rti exception4: rti exception5: rti exception6: rti exception7: rti