rem RPC-3xx networking rem Uses COM1 as network port rem To use com port 0 and get going faster, REM out the following lines: rem 130, 150, 1510, 1530 rem Line 1510 must still exist, so rem AFTER the line number rem Change the following lines rem 160 for COM 0 instead of 1 rem 1000 change COM$(1) to COM$(0) rem If your card does not have analog output, comment out line 2560 rem command D assumes a display. Adjust the CONFIG DISPLAY command rem at line 140 rem Demo program is limited to 5 commands. If adding more, change rem limit check in line 1210 rem Data packet to the card is: rem >ncd...ds rem Where rem = carriage return character 0DH rem > = command signature rem n = card number. May be number 0-9 or letter rem c = command. May be number, letter, or combination rem d...d = data as required for command rem s = optional checksum of string rem a ?? means ignore checksum rem Command types for this demo are: rem A = set line 8. Data following A is 0 or 1 rem Example: >00A0?? rem B = set analog output channel, data rem Example: >00B043?? rem |||-1 to 4 digits of data rem | - channel no 0 or 1 rem Shows how to convert a string number into one usable by rem BASIC rem C = return position from counter 0 or 1 rem Example: >00C0?? rem ||-counter # rem | - command rem Shows how to take a "real" number and convert it to a rem string. rem D = Send message to display port rem Example: >00DCheck station 5?? rem E = Power up acknowledge. Used to inform host of reset condition rem Example: >00E?? rem F = Is everything OK or is there a problem rem Example: >00F?? rem Command F returns an An. If n = 0, everything OK rem Error codes in STATUS are set somewhere else rem Routine clears STATUS when polled 100 STRING 2000,40 :REM allocate memory 120 $(0) = ">00" :REM assign card ID. It is modifed at line 150 125 $(3) = ">99" :REM All units go into safety mode REM set up RS485 port on board for 19200 rem NOTE: this is board dependent. Check your cards manual to make sure rem 130 CONFIG BAUD 1,1,2 rem set the display type for command D 140 config display 1 rem Read lines 0-3 to determine card address. rem Card number starts from ASCII '0' and goes up from there. rem 150 ASC($(0),3) = (lineb(5,2) .AND. 15)+48 REM declare tasking and define conditions REM To 1000 when either 40 characters are in or a recieved rem 160 ON COM$1,40,13,1000 160 on com$0,40,13,1000 300 GOTO 300 :REM hang out here REM Handle interrupt here REM Since all variables are global, local variables used here start REM with the letter 'o'. This helps prevent inadvertent value changes REM to other parts of the program rem 1000 $(1) = COM$(1) :REM get data 1000 $(1) = com$(0) rem Check for emergency safety mode code 1005 if str(8,$(1),$(3)) = 1 then 5000 REM see if card ID is in this packet REM If 0 returned, is not this card 1010 IF STR(8,$(1),$(0)) <> 1 THEN RETURN REM Parse out command. For this demo, assume REM it is only 1 letter long and starts with REM capital letter A. If command is negative REM can return a NAK (negative acknowledge) REM to sender or ignore it. 1020 OA = ASC($(1),4)-65 1030 IF OA < 0 then 1500 REM Make sure checksum is OK REM Add up values in string for length - 2 1040 ocksum = 0 1050 ole = str(0,$(1)) 1060 for oc = 1 to ole-2 1070 ocksum = asc($(1),oc) + cksum 1080 next rem strip off excess 1090 ocksum = ocksum .and. 0ffH REM Get checksum values REM IF second to last character is a ?, then don't check checksum REM convert last two characters into decimal 1100 oc = asc($(1),ole-1) :REM get first digit 1110 if oc = 63 then 1200 :rem if ?, skip rest of checksum test 1120 gosub 1600 :rem convert ASCII to number 1130 och = oc*16 :REM assign high byte first 1140 oc = asc($(1),ole) :rem get last hex digit 1150 gosub 1600 1160 oc = oc+och :rem make checksum value rem if last two digits don't sum to message, then return a negative rem acknowledge error and bail out 1170 if oc <> ocksum then $(2) = "N2" : goto 1510 rem Checksum is good REM If status command, go process it 1200 IF oa = 4 THEN 4000 1210 if oa > 5 then 1500 :REM if not in command, is error REM Check for valid power up acknowledge REM if not acknowledged, then state so 1220 if oflag = 0 then $(2) = "N3" : goto 1510 rem process command rem GOSUB's could also be used here. However, goto's are faster as rem exiting the routine makes a direct branch to the condition rem Cmdn letter A B C D E F 1240 on oa goto 2000,2500,3000,3500,4000,4500 rem If more commands, check for limit. If over, then subtract command rem and make another ON GOTO REM Common return point for successful completion of a command REM Return acknowledge to sender. REM Used for commands 1400 $(2)="A" 1410 GOTO 1510 :REM to common output & exit REM Return negative acknowledge to sender. REM N1 = unrecognized command REM N2 = checksum bad REM N3 = power up not acknowledged. Needs command 5. REM N4 = bad data REM N5 = something is wrong. Can add error conditons as needed 1500 $(2)="N1" 1510 rem UO1 1520 PRINT $(2) rem 1530 UO0 :REM back to main port 1540 RETURN REM convert ASCII HEX number into a number 0 - 15 REM Enter with oc = ASCII value of number (0-9 or A-F which is 48- REM 58 or 65 to 70) REM If problem, oc returns -1. If OK, returns number 0 to 15 1600 if (oc < 48) .or. (oc > 70) then oc = -1 : return 1610 if oc > 58 then 1640 rem value between 0 and 9. Simply subtract 48 and exit 1620 oc = oc-48 1630 return rem Value should be between A-F 1640 if oc < 65 then oc = -1 : return 1650 oc = oc - 55 1660 return REM Send back acknowledge 1700 $(2) = "A" 1710 GOTO 1510 rem Bad data 1750 $(2) = "N4" 1760 goto 1510 REM set a line according to data rem For this example, line 8 is assumed to be controlled rem Get desired status. Position 5 in string is 1 or 0 2000 oc = asc($(1),5) - 48 rem make sure data is 0 or 1 2010 if oc < 0 then 1750 2020 if oc > 1 then 1750 rem Set line according to input and send back acknowledge 2030 line 8,oc 2040 goto 1700 rem Command B rem Set analog output rem Command format: >XXBcdddd?? rem ||||||-dddd = data 1 to 4 numbers rem || - channel no. 0 or 1 rem | - this command no rem get the channel no. 2500 oc = asc($(1),5) - 48 rem Data starts at position 6 and could be 1-4 numbers long rem Extract the last part of the string into $(4) 2510 od =str(0,$(1)) :rem get length of string 2520 od =str(7,$(4),$(1),6,od-7) :rem get only data rem convert string number into usable number then output it rem Check limits. If out of range, then return error 2530 od = str(3,$(4)) 2540 if (od < 0) .or. (od > 4095) then 1750 2550 if (oc < 0) .or. (oc > 1) then 1750 2560 aot oc,od 2590 goto 1700 rem Command C rem Return counter value rem Command format: >xxCc?? rem |-counter number 0 or 1 (RPC-330) rem (could be 4-11 also) rem change limit check in 3010 for your card rem get the channel no. 3000 oc = asc($(1),5) - 48 3010 if (oc < 0) .or. (oc > 1 ) then 1750 3020 oc = count(oc) rem convert number to a string and output 3030 oc = str(10,$(2),0,oc) rem Force letter A to first spot. This is a space as set by format above 3040 asc($(2),1) = 65 rem output string as it is 3050 goto 1510 rem Command D rem Send string to display rem Command format: >xxDCheck station 2?? rem NOTE: Position is set by another command (exercise left to rem the student) rem Extract the string to display 3500 oc = str(0,$(1)) : rem get length 3510 oc = str(7,$(4),$(1),5,oc-6) 3520 display $(4) 3530 goto 1700 rem Set power up acknowledge flag (OFLAG) 4000 oflag = 1 4010 goto 1700 rem Command F rem General status of card rem Syntax: >xxF?? rem Returns An rem Where n = code or codes of system. 0 = all ok rem variable STATUS is global and indicates system status 4500 oc = str(10,$(2),0,status) rem Force letter A to first spot. This is a space as set by format above 4510 asc($(2),1) = 65 rem optionally clear STATUS flag 4520 status = 0 rem output string as it is 4530 goto 1510 rem Emergency or safety shut down rem Set lines as appropriate here rem Do not return an acknowledge as message applies to all rem cards on network 5000 rem shut down code here 5200 return