serial port issue

DOS specific questions.
Post Reply
ThisPlaceHere
Posts: 9
Joined: Dec 19, 2011 19:52
Location: Wisconsin

serial port issue

Post by ThisPlaceHere »

Hi all! I love FreeBasic!
I've written several little apps, and they all work great under XP or 2000. But I spent all of last week trying to get a new program to work under DOS. I installed Win95 to see what would happen, and it works better, but still not well.
I've got a program that continually talks to the serial port. Every 100ms. It's controlling a card (Ontrack ADR112) to operate a stepper motor, monitor buttons pressed, and read a loadcell (analog input). Like I mentioned, the program works perfectly under 2000 and XP. In pure Dos (MS 6.22) the program runs deathly slow. When I insert a routine to count loops and measure time between events, everything comes out funky.. like 3,000 loops when under windows it was 400 loops, 1.23E+08 instead of .102 when calculating Timer - oldTimer [=Timer stored before routine]. It's like time functions work differently under Dos? or are not Double type in Dos?
After trying the program in a Windows 95 dos box, things are improved, but not good enough yet. What I get here is a seeming Pause every time I read or write to the serial port. I send a string, and sometimes I get the correct response, other times no response, and sometimes I get back part of what I sent. I've played with buffer settings and how I'm sending/receiving and speeds and times and ... ??
I got nothing. And now I'm here.

I've ripped all of the graphical / mathematical stuff out of the program so all I have left is talking to the serial port. It works on and off. Seemingly at random. I hope someone can offer advice on getting this to work! Here's the routine that _seems_ to be the problem (with setup snipets):

Code: Select all

    Serial.Ok = 0 'set 1 when when return Ok, 0 if error
    Serial.Handle = FREEFILE

Open COM "COM1:9600,N,8,1,CS0,DS0,CD0,OP0,TB8,RB16,BIN,IR4" AS #Serial.Handle

Sub TxRx(Transmit As String, WaitResponse As Byte)
    Dim AS DOUBLE TimeEnd, TimeOut
    Dim AS STRING Character, Sample, Receive
    TimeOut = SerialPort.Timeout / 1000 'milliSeconds allowed for Transmit or Recieve
 
	Sample=""
	If (Serial.IsOpen = 1) Then
		Serial.Ok = 1
		' Empty the buffer.
      While (LOC(Serial.Handle) > 0)
         Sample = INPUT(1, Serial.Handle) 'read one character at a time
      Wend

      'Send the data.
      If Transmit <> "" THEN
         TimeEnd = Timer + TimeOut
         Print #Serial.Handle, Transmit
            If Timer > TimeEnd THEN
               Serial.Ok = 0
               Transmit = ""
            EndIf
         Transmit = ""
      End If
   
   	' Read the response if requested
      Receive = ""
      Response = ""
      If (WaitResponse = 1) And (Serial.Ok = 1) Then
      	Serial.Ok = 0
        TimeEnd = Timer + TimeOut
      	Do
            While (LOC(Serial.Handle) > 0)
         		Sample = INPUT(1, Serial.Handle) 'read one character at a time
                If (ASC(Sample) <= 31) Then 'found control code
		            If Receive <> "" Then
                        Response = Receive
            			Exit Do
		            EndIf
				Else
	              	Serial.Ok = 1
	              	Receive = Receive & Sample
                End If
	      	Wend
      		If Timer > TimeEnd THEN
                Serial.Ok = 0
                Receive = ""
            	Exit Do
      		EndIf
            sleep 1
      	Loop While (Timer < timeEnd)
      EndIf
	Else
		Serial.Ok = 0
	EndIf
END SUB
For example, if I continuoulsy (every 100msec) TxRx("PA",1), I get Response= (seemingly randomly) nothing, "128" (proper), or "A0".
Richard
Posts: 3096
Joined: Jan 15, 2007 20:44
Location: Australia

Post by Richard »

I think the difference is in the step rate of the Timer between DOS and Windows.
See the Timer keyword documentation.
Search this forum for more work-arounds.

Here is an extract of part doco...
"
The precision of TIMER varies, depending on the computer used. If the processor has a precision timer (as the Performance Counter Pentium processors from Intel have) and the OS uses it, the precision is linked to the processor clock and microseconds can be expected. With older processors (386, 486), and always in DOS, the resolution is 1/18 second.
Usage of TIMER can cause disk accesses in DOS, see forum for analysis and solutions
In QB TIMER returned the number of seconds from last midnight, and its accuracy was 1/18 secs
"
ThisPlaceHere
Posts: 9
Joined: Dec 19, 2011 19:52
Location: Wisconsin

Post by ThisPlaceHere »

This afternoon/evening I read all about the timer issues, and used the hrtimer routine from these message boards and now I can properly see time going by... so now I can confirm my problem has to do with the serial communication. Sometimes I get hung on output, sometimes hung on input. I've fiddled with all the parameters of the open com statement, slowed down the writing/reading to/from the serial port.. but nothing seems to change. Next I'm going to try some other machines to see if I can narrow anything down as far as hardware or operating systems causing my problems.
Richard
Posts: 3096
Joined: Jan 15, 2007 20:44
Location: Australia

Post by Richard »

It was a very long time ago, but I seem to recall that satisfying or defeating the physical hardware handshake is slightly different between DOS and Windows. I'm sorry if I am misleading you.
Maybe for a clue, take a look at http://www.freebasic.net/forum/viewtopic.php?p=117518
ThisPlaceHere
Posts: 9
Joined: Dec 19, 2011 19:52
Location: Wisconsin

Solved.

Post by ThisPlaceHere »

Okay. A few different computers and OSes and here's what I've found.
Running pure dos [6.22] with the CWSDPMI doesn't seem to let the serial port work correctly. Running inside a windows dos box, serial runs very slow (windows time sharing?). If I boot to windows 95 command prompt only, the serial port works perfectly! So, the target machine is now "Windows95 Dos" and all of the graphics and serial commands are running smooth.

In case someone finds this article looking for help on serial communication in DOS, I would mention that I had nothing at all until I connected the CTS+RTS and DTR+DSR pins together (my device uses only TX,RX,Gnd). Follow the link that Richard provided to go into this.
Thanks!
Post Reply