??? 05/20/07 03:47 Modified: 05/20/07 03:48 Read: times |
#139550 - Sunday Challenge (rev 4) Responding to: ???'s previous message |
Okay, we made it work. Now, just for fun, let's try to make it as small as possible (probably at the expense of structure and maintainability and all that good stuff). This version follows the pattern of Jan's original "rev 1" pretty closely, except that TxChar is a subroutine instead of inline, and I came up with bit of a stunt for sending the backspace-space-backspace sequence at EatChar.
This version occupies 64 bytes. Can anybody make an equivalent routine that's shorter? -- Russ 00AC ReceiveString: 00AC 7800 mov r0,#RxBuffer ; Initialize receiver pointer 00AE GetNextChar: ; Come here to get each new character 00AE 3098FD jnb RI0,$ ; Wait for incoming character 00B1 C298 clr RI0 ; Clear flag 00B3 E599 mov A,SBUF ; Got it 00B5 20E7F6 jb acc.7,GetNextChar ; It's unprintable (>= 80h) - ignore it 00B8 B42000 cjne a,#20h,$+3 ; Is it a control character (<20h)? 00BB 400E jc ControlChars ; Yes - process separately 00BD B80907 cjne r0,#BUFFER_END,SaveChar ; No - go store if no overflow 00C0 BeepAndGet: 00C0 7407 mov a,#BEEP_CHR ; Buffer overflow if we get here 00C2 TxAndGet: 00C2 1200E4 call TxChar ; Make the terminal beep 00C5 80E7 sjmp GetNextChar ; Go get next character 00C7 SaveChar: ; Printable character if we get here 00C7 F6 mov @r0,a ; Put character in buffer 00C8 08 inc r0 ; Advance buffer pointer 00C9 80F7 sjmp TxAndGet ; Go echo character, then get another 00CB ControlChars: ; Control character if we get here 00CB B40810 cjne a,#BS_CHR,NotBackSpace ; Not backspace - press on 00CE B80002 cjne r0,#RxBuffer,EatChar ; Is backspace - go eat if no underflow 00D1 80ED sjmp BeepAndGet ; Go beep, then get next character 00D3 EatChar: ; Process backspace here 00D3 18 dec r0 ; Remove the character from the buffer 00D4 EatLoop: 00D4 1200E4 call TxChar ; Send BS-SPACE-BS to terminal to erase 00D7 6428 xrl a,#BS_CHR XOR SPACE_CHR ; the most recently typed character 00D9 B408F8 cjne a,#BS_CHR,EatLoop 00DC 80E4 sjmp TxAndGet ; Go get next character 00DE NotBackSpace: ; Control char, but not backspace 00DE B40DCD cjne a,#CR_CHR,GetNextChar ; If not CR, go get next character 00E1 7600 mov @r0,#0 ; Got CR - terminate the string 00E3 22 ret ; Done 00E4 TxChar: 00E4 F599 mov SBUF,A ; Send the character 00E6 3099FD jnb TI0,$ ; Spin until it's sent 00E9 C299 clr TI0 ; Reset done flag 00EB 22 ret ; Done 00EC end |