OpenCores
URL https://opencores.org/ocsvn/light8080/light8080/trunk

Subversion Repositories light8080

[/] [light8080/] [trunk/] [sw/] [tb/] [soc_tb/] [soc_tb.lst] - Rev 85

Go to most recent revision | Compare with Previous | Blame | View Log

0001   0000             ;*******************************************************************************
0002   0000             ; soc_tb.asm -- light8080 SoC basic test bench.
0003   0000             ;*******************************************************************************
0004   0000             ; Should be used with SoC core test bench entity vhdl\test\l80soc_tb.vhdl.
0005   0000             ; Assembler format compatible with TASM for DOS and Linux.
0006   0000             ;*******************************************************************************
0007   0000             ; This program will send a few bytes over a looped-back UART, using the UART 
0008   0000             ; interrupt capability and verifying that received and transmitted data match.
0009   0000             ; It will then try one of the external interrupts, connected to one of the 
0010   0000             ; general purpose outputs.
0011   0000             ; This minimal test bench relies on an already tested CPU core to do a 
0012   0000             ; This program does not deserve to even be called a 'test' but if if works it 
0013   0000             ; will at least rule out many obvious bug in the SoC core.
0014   0000             ;*******************************************************************************
0015   0000             
0016   0000             ; DS pseudo-directive; reserve space in bytes, without initializing it
0017   0000             #define ds(n)    \.org $+n
0018   0000             
0019   0000             MASK_RX_IRQ:  .equ 20h
0020   0000             MASK_TX_IRQ:  .equ 10h
0021   0000             MASK_RX_RDY:  .equ 02h
0022   0000             MASK_TX_RDY:  .equ 01h
0023   0000             
0024   0000             UART_DATA:    .equ 80h
0025   0000             UART_STATUS:  .equ 81h
0026   0000             UART_BAUDL:   .equ 82h
0027   0000             UART_BAUDH:   .equ 83h
0028   0000             IRQ_ENABLE:   .equ 88h
0029   0000             
0030   0000             P1IN:         .equ 84h
0031   0000             P2OUT:        .equ 86h
0032   0000             
0033   0000             
0034   0000             ;*******************************************************************************
0035   0000             
0036   0000                       .org  0H              ; Reset entry point
0037   0000 C3 60 00              jmp   start           ; Skip the rst address area
0038   0003                                     
0039   0003                     ;***** Interrupt vectors in area 0008h-0038h *****************
0040   0003                       
0041   0008                       .org  0h+(1*8)        ; interrupt vector 1 (IRQ0)
0042   0008 C3 12 01              jmp   isr0
0043   0010                       .org  0h+(2*8)        ; interrupt vector 2
0044   0010 FB                    ei
0045   0011 C9                    ret
0046   0018                       .org  0h+(3*8)        ; interrupt vector 3 (IRQ1)
0047   0018 C3 1E 01              jmp   isr1
0048   0020                       .org  0h+(4*8)        ; interrupt vector 4
0049   0020 FB                    ei
0050   0021 C9                    ret
0051   0028                       .org  0h+(5*8)        ; interrupt vector 5 (IRQ2)
0052   0028 FB                    ei
0053   0029 C9                    ret
0054   0030                       .org  0h+(6*8)        ; interrupt vector 6
0055   0030 FB                    ei
0056   0031 C9                    ret
0057   0032                       
0058   0038                       .org  0h+(7*8)        ; interrupt vector 7 (IRQ3, UART)
0059   0038 C3 2A 01    int38h:   jmp   irq_uart        ; UART interrupt 
0060   003B                    
0061   003B                       ;***** program entry point *******************************************
0062   003B                             
0063   0060             start:    .org  60H
0064   0060 31 DA 01              lxi   sp,stack
0065   0063             
0066   0063                       ; Initialize UART RX and TX buffers
0067   0063 21 74 01              lxi   h,void_buffer
0068   0066 22 75 01              shld  ptr_tx
0069   0069 21 7A 01              lxi   h,rx_buffer
0070   006C 22 77 01              shld  ptr_rx
0071   006F 3E 00                 mvi   a,00h
0072   0071 32 79 01              sta   len_rx
0073   0074                       
0074   0074                       ; Clear all P2 output lines (used to simulate external interrupts)
0075   0074 3E 00                 mvi   a,00h
0076   0076 D3 86                 out   P2OUT
0077   0078                       
0078   0078                       ; Set up interrupts
0079   0078 3E 0B                 mvi   a,0bh           ; Enable UART irq plus IRQ0 and IRQ1...
0080   007A D3 88                 out   IRQ_ENABLE
0081   007C FB                    ei                    ; ...and enable interrupts in the CPU
0082   007D                     
0083   007D                       ; print hello message to console
0084   007D 21 02 01              lxi   h,msg_hello
0085   0080 CD 66 01              call  print_string
0086   0083                       ; Ok, now the message is being transferred through the looped back
0087   0083                       ; UART, using the UART interrupts, which have the lowest priority.
0088   0083                       ; We have plenty of time to make a few tests on the external interrupt
0089   0083                       ; lines before the message transmission is finished.
0090   0083                       
0091   0083                       ; The irq routines will leave some data at 'irq_data, each routine a
0092   0083                       ; different value and all non-zero. This is how we know what irq 
0093   0083                       ; routines have executed and in which order.
0094   0083                       
0095   0083                       ; Test IRQ0 alone 
0096   0083 3E 01                 mvi   a,01h           ; Initialize irq data 
0097   0085 32 73 01              sta   irq_data
0098   0088 3E 01                 mvi   a,01h           ; Trigger IRQ0
0099   008A D3 86                 out   P2OUT
0100   008C             test_irq0:
0101   008C 3A 73 01              lda   irq_data        
0102   008F FE 04                 cpi   004h            ; Do we see the IRQ test data?
0103   0091 CA 9C 00              jz    done_irq0       ; If we do, proceed to next test 
0104   0094 FE 01                 cpi   001h            ; Do we see some other IRQ test data instead?
0105   0096 C2 FB 00              jnz   test_fail       ; If we do, there's trouble with the irqs
0106   0099 C3 8C 00              jmp   test_irq0       ; Keep waiting for some IRQ test data
0107   009C             done_irq0: 
0108   009C 3E 00                 mvi   a,00h           ; Deassert all interrupt lines
0109   009E D3 86                 out   P2OUT
0110   00A0                       
0111   00A0                       ; Test IRQ1 alone 
0112   00A0 3E 01                 mvi   a,01h           ; Initialize irq data 
0113   00A2 32 73 01              sta   irq_data
0114   00A5 3E 02                 mvi   a,02h           ; Trigger IRQ1
0115   00A7 D3 86                 out   P2OUT
0116   00A9             test_irq1:
0117   00A9 3A 73 01              lda   irq_data        
0118   00AC FE 02                 cpi   002h            ; Do we see the IRQ test data?
0119   00AE CA B9 00              jz    done_irq1       ; If we do, proceed to next test 
0120   00B1 FE 01                 cpi   001h            ; Do we see some other IRQ test data instead?
0121   00B3 C2 FB 00              jnz   test_fail       ; If we do, there's trouble with the irqs
0122   00B6 C3 A9 00              jmp   test_irq1       ; Keep waiting for some IRQ test data
0123   00B9             done_irq1: 
0124   00B9 AF                    xra   a               ; Deassert all interrupt lines
0125   00BA D3 86                 out   P2OUT
0126   00BC                       
0127   00BC                       ; Test IRQ0 and IRQ1 simultaneously
0128   00BC 3E 01                 mvi   a,01h           ; Initialize irq data 
0129   00BE 32 73 01              sta   irq_data
0130   00C1 3E 03                 mvi   a,03h           ; Trigger IRQ0 and IRQ1 
0131   00C3 D3 86                 out   P2OUT
0132   00C5                       
0133   00C5                       ; Sequence IRQ0->IRQ1 will result in (1 << 2) + 1 = 5
0134   00C5                       ; Sequence IRQ1->IRQ0 would result in (1 + 1) << 2 = 6
0135   00C5                       ; We expect IRQ0->IRQ1, since IRQ0 has higher priority
0136   00C5             test_irq01:
0137   00C5 3A 73 01              lda   irq_data        
0138   00C8 FE 05                 cpi   005h            ; Do we see the IRQ0->IRQ1 test data?
0139   00CA CA D5 00              jz    done_irq01      ; If we do, proceed to next test 
0140   00CD FE 01                 cpi   001h            ; Do we see some other IRQ test data instead?
0141   00CF C2 FB 00              jnz   test_fail       ; If we do, there's trouble with the irqs
0142   00D2 C3 C5 00              jmp   test_irq01      ; Keep waiting for some IRQ test data
0143   00D5             done_irq01: 
0144   00D5 AF                    xra   a               ; Deassert all interrupt lines
0145   00D6 D3 86                 out   P2OUT
0146   00D8                       
0147   00D8                       ; Ok, the external interrupts have been tested (well, 'tested'). Now
0148   00D8                       ; wait for the UART looped-back transmission to end and compare 
0149   00D8                       ; the data.
0150   00D8             
0151   00D8                       ; Wait until the number of UART received characters equals the length 
0152   00D8                       ; of the test message.
0153   00D8             wait_for_message:          
0154   00D8 3A 79 01              lda   len_rx
0155   00DB FE 0F                 cpi   msg_len
0156   00DD C2 D8 00              jnz   wait_for_message
0157   00E0                       
0158   00E0                       ; Compare the TX and RX strings
0159   00E0 21 7A 01              lxi   h,rx_buffer
0160   00E3 11 02 01              lxi   d,msg_hello
0161   00E6             compare_loop:
0162   00E6 1A                    ldax  d
0163   00E7 FE 24                 cpi   '$'
0164   00E9 CA F5 00              jz    test_ok
0165   00EC BE                    cmp   m
0166   00ED C2 FB 00              jnz   test_fail
0167   00F0 23                    inx   h
0168   00F1 13                    inx   d
0169   00F2 C3 E6 00              jmp   compare_loop
0170   00F5                       
0171   00F5                       
0172   00F5                       
0173   00F5                       
0174   00F5                       
0175   00F5             test_ok:          
0176   00F5 3E 80                 mvi   a,80h           ; Raise 'success' output flag...
0177   00F7 D3 86                 out   P2OUT
0178   00F9 F3          done:     di                    ; ...and block here.
0179   00FA 76                    hlt                   
0180   00FB             
0181   00FB             test_fail:
0182   00FB 3E 40                 mvi   a,40h           ; Raise 'failure' flag...
0183   00FD D3 86                 out   P2OUT
0184   00FF C3 F9 00              jmp   done            ; ...and block.
0185   0102                       
0186   0102                       
0187   0102             
0188   0102 0A 0D 0A 48 msg_hello: .text "\n\r\nHello World!$"     
0188   0106 65 6C 6C 6F 
0188   010A 20 57 6F 72 
0188   010E 6C 64 21 24 
0189   0112             msg_end:  .equ $
0190   0112             msg_len:  .equ msg_end - msg_hello - 1    
0191   0112             
0192   0112 F5          isr0:     push  psw
0193   0113 3A 73 01              lda   irq_data
0194   0116 07                    rlc
0195   0117 07                    rlc
0196   0118 32 73 01              sta   irq_data
0197   011B F1                    pop   psw
0198   011C FB                    ei
0199   011D C9                    ret
0200   011E             
0201   011E F5          isr1:     push  psw
0202   011F 3A 73 01              lda   irq_data
0203   0122 C6 01                 adi   1
0204   0124 32 73 01              sta   irq_data
0205   0127 F1                    pop   psw
0206   0128 FB                    ei
0207   0129 C9                    ret
0208   012A                       
0209   012A             ;irq_uart: UART interrupt processing 
0210   012A             irq_uart:
0211   012A E5                    push  h
0212   012B F5                    push  psw
0213   012C                       
0214   012C                       ; Deal with RX interrupt (if any) first and then the TX interrupt.
0215   012C DB 81                 in    UART_STATUS     ; Is there new data in the RX register?
0216   012E E6 20                 ani   MASK_RX_IRQ
0217   0130 CA 48 01              jz    irq_uart_rx_done ; If there isn't, process TX interrupt.
0218   0133                       
0219   0133                       ; Process UART RX interrupt
0220   0133             irq_uart_rx:     
0221   0133 3E 20                 mvi   a,MASK_RX_IRQ   ; Clear IRQ flag.
0222   0135 D3 81                 out   UART_STATUS     
0223   0137 DB 80                 in    UART_DATA       ; Get RX byte...
0224   0139 2A 77 01              lhld  ptr_rx          ; ...and store it in the rx buffer.
0225   013C 77                    mov   m,a
0226   013D 23                    inx   h
0227   013E 22 77 01              shld  ptr_rx          ; Update the rx buffer pointer.
0228   0141 3A 79 01              lda   len_rx          ; Update RX buffer length
0229   0144 3C                    inr   a
0230   0145 32 79 01              sta   len_rx 
0231   0148                       
0232   0148                       ; Note there's no check for RX buffer overrun! we shouldn't need it 
0233   0148                       ; here, a runaway condition would be readily apparent in the 
0234   0148                       ; simulation, anyway.
0235   0148             
0236   0148             irq_uart_rx_done:
0237   0148                       ; Ok, RX is done. Now deal with TX irq, if any
0238   0148 DB 81                 in    UART_STATUS     ; Is the TX buffer re new data in the RX register?
0239   014A E6 10                 ani   MASK_TX_IRQ
0240   014C CA 62 01              jz    irq_uart_end    ; If there isn't, we're done.
0241   014F                       
0242   014F                       ; process UART TX interrupt
0243   014F             irq_uart_tx:
0244   014F 3E 10                 mvi   a,MASK_TX_IRQ   ; Clear IRQ flag.
0245   0151 D3 81                 out   UART_STATUS
0246   0153 2A 75 01              lhld  ptr_tx          ; Get next byte from the TX buffer 
0247   0156 7E                    mov   a,m
0248   0157 FE 24                 cpi   '$'             ; Did we reach the end of the buffer?
0249   0159 CA 62 01              jz    irq_uart_tx_done ; If we did, we're done here...
0250   015C 23                    inx   h               ; ...otherwise increment the TX pointer...
0251   015D 22 75 01              shld  ptr_tx
0252   0160 D3 80                 out   UART_DATA       ; ...and transmit the data byte.
0253   0162                       
0254   0162             irq_uart_tx_done:
0255   0162                     
0256   0162             irq_uart_end:
0257   0162 F1                    pop   psw             ; Done, quit.
0258   0163 E1                    pop   h
0259   0164 FB                    ei
0260   0165 C9                    ret                
0261   0166                     
0262   0166             ;print_string: print $-terminated string at HL
0263   0166             print_string:
0264   0166                       ; We don't check if there's a transmission going on
0265   0166 7E                    mov   a,m             ; Get first character from string...
0266   0167 23                    inx   h               ; ...and move updated string pointer to TX  
0267   0168 22 75 01              shld  ptr_tx          ; buffer pointer.
0268   016B FE 24                 cpi   '$'             ; Kickstart transmission by sending 1st byte...
0269   016D CA 72 01              jz    print_string_end; ...unless its the end of string marker.
0270   0170 D3 80                 out   UART_DATA       ; 
0271   0172             print_string_end:
0272   0172 C9                    ret
0273   0173             
0274   0173                       
0275   0173                       ; data space, placed immediately after object code in memory
0276   0173             irq_data:     ds(1)
0276   0174             
0277   0174 24          void_buffer:  .text "$"
0278   0175             ptr_tx:       ds(2)
0278   0177             
0279   0177             ptr_rx:       ds(2)
0279   0179             
0280   0179             len_rx:       ds(1)
0280   017A             
0281   017A             rx_buffer:    ds(32)
0281   019A             
0282   019A                           ds(64)
0282   01DA             
0283   01DA             stack:        ds(2)
0283   01DC             
0284   01DC                       .end
0285   01DC                     tasm: Number of errors = 0

Go to most recent revision | Compare with Previous | Blame | View Log

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.