Struggling with serial comms
#1
<!-- @page { margin: 2cm } P { margin-bottom: 0.21cm } -->
I am having a problem with one of the example 'Help' programmes. Under LOC 'Help' is a simple programme for RS232 communication with a peripheral via COM1.

OPEN "COM1: 9600,N,8,1,OP0" FOR RANDOM AS #1 LEN = 2048 ' random mode = input and output
  DO: t$ = INKEY$ ' get any transmit keypresses from user
    IF LEN(t$) THEN PRINT #1, t$ ' send keyboard byte to transmit buffer
    bytes% = LOC(1) ' bytes in buffer
    IF bytes% THEN ' check receive buffer for data"
      r$ = INPUT$(bytes%, 1)          ' get bytes in the receive buffer
      PRINT r$; ' print byte strings consecutively to screen"
    END IF   
  LOOP UNTIL t$ = CHR$(27) 'escape key exit
CLOSE #

My peripheral is a Summagraphics digitising pad - this has a movable puck with four buttons; you position the puck, press one of the buttons, and it sends the numeric x y coordinates of the puck and a numeric flag for the button to its RS232 port in effectively csv format. Thus the output may be  16958,11142,1<CR><LF>  for one press, ie 15 bytes. It also receives input from its RS232 port to configure it. It is thus acting very like a modem.

The above programme in QB64 2.0.2 fails at line 17 with the message "Bad file mode" when I press a keyboard key. Clearly it doesn't like the "Print #1" command.

Which I am not surprised at because isn't "Print #n" a sequential file command and the comms buffer has been opened as "Random"?

And then - if I eliminate the 't$=' and 'IF Len' lines to concentrate on the receive, I get an 'Input past end of file' error at the 'r$=" line, despite LOC returning 15 bytes in the buffer. If I overwrite bytes% with 1, to get the first character in the buffer, I still get 'Input past end of file'.

What is going on? Are these bugs? Any help gratefully received.
Reply
#2
(05-05-2022, 11:01 AM)I've implemented these function to handle serial: Wrote:
Code: (Select All)
Function ser.open% (ser$) ' e.g. ser$="COM1:9600"
  On Error GoTo Errhandler
  Open ser$ + ",N,8,1,BIN,CS0,DS0,RB8192" For Random As #88
  If errorNum = 0 Then serBytes$ = ser.read$
  On Error GoTo 0
  ser.open% = errorNum
End Function

Function ser.close$ ()
  ser.close$ = ser.read$
  Close #88
End Function

Sub ser.send (bytes$)
  Dim b As String * 1
  For i% = 1 To Len(bytes$)
    b = Mid$(bytes$, i%, 1)
    Put #88, , b
  Next i%
End Sub

Function ser.read$ ()
  Dim b As String * 1: resp$ = ""
  Do While Loc(88)
    Get #88, , b: resp$ = resp$ + b
  Loop
  ser.read$ = resp$
End Function
Most important parts:
",BIN,CS0,DS0,RB8192" in open statement
to read:  Do While Loc(88):Get #88, , b: resp$ = resp$ + b:Loop
to write:   Dim b As String * 1:b = Mid$(bytes$, i%, 1)Tongueut #88, , b
45y and 2M lines of MBASIC>BASICA>QBASIC>QBX>QB64 experience
Reply
#3
Thanks very much - I'll try it.

Doesn't address the fact that the help example seems to be junk though!!!
Reply
#4
(05-05-2022, 03:06 PM)Wolstan Dixie Wrote: Thanks very much - I'll try it.

Doesn't address the fact that the help example seems to be junk though!!!

As a wiki editor, I take offense at your statement... Oh wait, that looks like something Clippy wrote. You're right, it's junk! Kidding aside, it's probably just too outdated. Windows put some real pressure on the way QB can access ports. Please let us know if the solution provided works for you, and I'll talk to Rho about updating the help page.

Oh, and md... when did [Image: tongue.png]ut become a qb64 keyword? Something Steve added? Big Grin

Pete
Reply
#5
Yes - that works OK. But why do you read the strings a byte at a time, rather than the whole string in one go?
Reply
#6
Because in my struggles to get it stable and reliable, this worked out best ;-)
45y and 2M lines of MBASIC>BASICA>QBASIC>QBX>QB64 experience
Reply
#7
(05-06-2022, 10:43 AM)mdijkens Wrote: Because in my struggles to get it stable and reliable, this worked out best ;-)

HA! - I can relate to that!

Thanks
Reply
#8
(05-06-2022, 10:43 AM)mdijkens Wrote: Because in my struggles to get it stable and reliable, this worked out best ;-)

Been there, done that! That rated a thumbs up from me. Job one, get it working. Makeovers come later.

Pete
Reply
#9
(05-05-2022, 01:55 PM)mdijkens Wrote:
(05-05-2022, 11:01 AM)Thanks mdijkens, your example is just what I was looking for.  I was using Liberty Basic for my application which will let you open a serial port as random and use Print and Input type commands.  Weird... but it actually works.  With QB64 I needed to be a Get'n and a Put'n and thus the need for your example. Wrote: Thanks again... Bill
Reply




Users browsing this thread: 1 Guest(s)