REM Very simple async terminal. Series 5 version. REM you can test this with Windows terminal or similar. PROC terminal: GLOBAL k&(16) GLOBAL SerReadWaiting%,EvntReadWaiting% GLOBAL SerRxBuf$(100),KeybBuf$(100) GLOBAL sfg%,ser%,evnt% LOCAL ret%,c% TRAP LOPEN("TTY:A") IF ERR=-40 ret%=ALERT("Link in use.") REM you can put code here to close link before trying REM to open serial port again. STOP REM close link code not present! ELSEIF ERR<>0 ret%=ALERT("Serial Port problem:",ERR$(ERR)) STOP ENDIF set232:(15,0,8,0) REM 9600, no parity, 8bit, RTS/CTS REM you must not have more than 1 IOA to the same device outstanding, REM EvntReadWaiting% and SerReadWaiting% prevent this from happening. EvntReadWaiting%=0 REM set flag to allow event read to be set up. SerReadWaiting%=0 REM likewise for serial read. KeybBuf$="" SerRxBuf$="" PRINT "Press Control-E to quit." DO REM If no serial read is oustanding, REM queue an async read for 1 byte. IF SerReadWaiting%=0 c%=1 IOC(-1,1,ser%,#ADDR(SerRxBuf$)+1,c%) SerReadWaiting%=1 REM disallow a further serial read ENDIF REM If no event read is outstanding, REM set up an async read for one keyboard or system event. IF EvntReadWaiting%=0 GETEVENTA32 evnt%,k&() EvntReadWaiting%=1 REM disallow a further read ENDIF IOWAIT REM wait for a serial, keyboard, or system event. REM ser% will remain at -46 until a byte has been received. REM So if it is not -46, at least one byte received. IF ser%<>-46 SerReadWaiting%=0 REM allow another ser read c%=1 REM number of bytes to read = 1 POKEB ADDR(SerRxBuf$),c% PRINT SerRxBuf$; IOW(-1,10,c%,#0) REM checks how many serial bytes waiting to be read, REM you can use IOW as service 10 returns immediately REM This next line limits the next IOW to read 80 chars REM c% should be less than the SerRxBuf$ size. If you REM don't read all the bytes, the rest will be read REM next time round... IF c%>80 :c%=80 :ENDIF IF c%>0 REM If one or more bytes waiting... REM IOW can be used since as we know c% chars REM are waiting, the call returns immediately. REM So now read c% bytes: IOW(-1,1,#ADDR(SerRxBuf$)+1,c%) POKEB ADDR(SerRxBuf$),c% PRINT SerRxBuf$; ENDIF ENDIF REM Now check if any keyboard/system events have been received. IF evnt%<>-46 REM not -46, therefore something has happened. EvntReadWaiting%=0 REM allow further event read IF k&(1)=$404 REM system shutdown received. REM put tidy up code here. LCLOSE STOP ELSEIF (k&(1) AND $400)=0 REM a letter key has been pressed IF k&(1)<27 REM It's probably a Ctrl-modified key IF k&(1)=8 OR k&(1)=13 REM if a delete or enter key dotxt$:(k&(1)) ELSE REM deal with commands here: docmd:(k&(1)) ENDIF ELSE REM ordinary letter keys dotxt$:(k&(1)) ENDIF ENDIF ENDIF UNTIL 0 ENDP PROC set232:(baud%,parity%,data%,hand%) REM This procedure (c/o Psion UK) is in the OPL programming manual. REM Sets up RS232 port. LOCAL srchar%(6),dummy%,r%,frame% frame%=data%-5 IF parity% :frame%=frame% OR 32 :ENDIF srchar%(1)=baud% OR (baud%*256) srchar%(2)=frame% OR (parity%*256) srchar%(3)=(hand% AND 255) OR $1100 srchar%(4)=$13 IOW(-1,7,srchar%(1),dummy%) ENDP PROC dotxt$:(char&) REM saves keys pressed into KeybBuf$, and sends this REM to the serial port when Enter is pressed. REM NOTE that there is no check for overflow of KeybBuf$ !! REM You should make sure that this cannot happen; either send REM the string as it is, or use some method to stop it getting REM too big. LOCAL c%,p% c%=1 rem CURSOR 1 IF char&<>13 AND char&<256 REM ascii character. KeybBuf$=KeybBuf$+CHR$(char&) REM build up string to send... PRINT CHR$(char&); REM print character to screen ELSEIF char&=13 REM Enter pressed. REM send KeybBuf$ to serial port. KeybBuf$=KeybBuf$+CHR$(13) REM add CR if necessary. sendtxt: ENDIF ENDP PROC sendtxt: REM sends KeybBuf$ to serial port. LOCAL c% : rem holds length of KeybBuf$ c%=LEN(KeybBuf$) REM The following MAY be required. These two lines will cancel REM an outstanding serial read, before a serial send. REM They MAY prevent corruption of echoed data, if this occurs. REM IOCANCEL(-1) REM SerReadWaiting%=1 REM If sfg% is -46, then the last send has not yet completed. REM Probably something wrong, like remote device not connected!! IF sfg%<>-46 REM If it's not -46, we can send another string. IOC(-1,2,sfg%,#ADDR(KeybBuf$)+1,c%) : rem send bytes to RS232 KeybBuf$="" REM clear string ELSE REM last string not sent yet... BEEP 3,300 gIPRINT "TX Error!" ENDIF ENDP PROC docmd:(comd&) REM Deals with Control modified keys... IF comd&=5 REM Control-E dINIT "Quit?" dBUTTONS "No",-($300+%n),"Yes",%y+$300 IF dIALOG LCLOSE STOP ENDIF ENDIF ENDP