More questions on logging Comm data
More questions on logging Comm data
More questions on logging Comm data
More questions on logging Comm data
More questions on logging Comm data
More questions on logging Comm data More questions on logging Comm data More questions on logging Comm data More questions on logging Comm data More questions on logging Comm data More questions on logging Comm data More questions on logging Comm data More questions on logging Comm data
More questions on logging Comm data More questions on logging Comm data
More questions on logging Comm data
Go Back  Xtreme Visual Basic Talk > > > More questions on logging Comm data


Reply
 
Thread Tools Display Modes
  #1  
Old 06-27-2006, 07:37 PM
fredy989q fredy989q is offline
Regular
 
Join Date: Sep 2004
Posts: 57
Default More questions on logging Comm data


DougT was able to help me out on Get and Put to binary files. But I am still having trouble parsing my incoming data streams.

I am using MSComm controls to send to (the host) and receive from (the client) an instrument simulator; using two programs I am creating with VB6. When this is working I will ship the host software to a distant location where a collaborator will connect with the real hostpital laboratory instrument and log my dialog attempts.

Communications is half-duplex using packets that start with a nul (0x00) and end with a VBcr (0x0d); neither of which characters are prohibited in certain other packet positions. The length of the packets is determined by a lookup table based upon the second, and possibly another, byte in the packet (depending upon the value of the second byte). There is no handshaking involved. I need to log the communications dialog to a screen text box and to a binary file to debug the host VB code. The client protocol is reasonably well defined by the manufacturer.

My problem is in using the MScomm control features to parse the reply packets. I believe I need to parse the replies one byte at a time in order to be able to determine packet length. For this I believe I need to set the Receive Threshold at 1, the InputMode to comInputModeText and InputLen to 1 while processing every comEvReceive interrupt event. Because each packet character can have a multitude of interpretations I plan to just log the hex value stream for now.

At this point I am all tangled up in ASC vs CHR vs byte number vs arrays vs ubounds vs redims vs strings and what seems like a million permutations, none of which seem to work right! Please help me with the MSComm settings to get one interrupt (comEvReceive) per character, one character per interrupt, and how to recover at least the decimal value of each incoming character. I must not lose the character position regardless of the character value (including 0x00) so that I will know where I am in a packet at all times.

I have really given up on trying to manage dynamic byte arrays!

I really don't understand why this is so difficult!!!!

My current resources are "Using the (MsComm) Communications Control" and Xtreme Visual Basic Talk > Legacy VB > Knowledge Base > Tutor's Corner > File IO.
Reply With Quote
  #2  
Old 06-28-2006, 01:17 AM
DougT's Avatar
DougT DougT is offline
Ultimate Antique

Administrator
* Expert *
 
Join Date: Sep 2005
Location: Maldon,Essex, UK
Posts: 3,939
Default

Hi,

I'll start off by saying that I've never used the MSComm control in anger so I can't give you much help with that. However, from a communications point of view, the description of the protocol you have given would lead me to believe that it's one that was designed for a hardware handshaking environment if the record 'start' header and record 'stop' header characters can appear within the records as legal characters.
When you read a 'start' character how do you know it's a 'start' and not part of the data ? The implication is that you have to treat the incoming data as one stream, ie the very first 'start' character is the only one you can 'trust' and everything that follows is effectively synchronised by that. In a real world environment, which you imply this is going to be, this could lead to all sorts of problems if there are any sort of errors in the transmission, you could (will) loose synchronisation and that will lead, at best to the programs aborting, and at worst, incorrect results - which in a Medical Lab environment, should be avoided.

Your life would me made much easier if the client device could drop DSR or whatever after it has sent a logical 'record'

Anyway, given that's the situation you're in and you have to treat the data as a stream, you will have to unblock into 'records'. For unblocking purposes all 'start' characters after the first one are irrelevant, as are 'stop' characters. Once you have the length of 'record N' you automatically know where 'record N+1' starts. (ie where you are + length of record N)

From my limited understanding of MSComm and looking at the documentation (http://msdn.microsoft.com/library/en.../vbobjComm.asp) "Setting RThreshold to 1, for example, causes the MSComm control to generate the OnComm event every time a single character is placed in the receive buffer."
(Mind you I think I have seen 'problems' reported that even with RThreshold set to one it is possible that more than one character is actually in the buffer when the .Input property is examined)

Using InputMode = comInputModeBinary causes a Byte Array to be populated with the input data which, I suggest, should be used in your case.

Having received the first character in the stream and identified it as a 'start' character you will have to manage some processes:
  • continue reading data until you have enough information to identify the length of this 'record'
  • continue reading data until you have read all the characters for this record
  • once (b) is satisfied, log the record to the file. (You may have to make adjustments depending on whether the length of the 'record' includes or excludes the 'start' and 'end' characters)
  • empty the array the data is being read into
  • check the next character to make sure it's a 'start' character and go back to (a)

As far as Chr() and Asc() are concerned, don't get too tied up with them. Going back to basics, everything in memory is held as sets of 8 bit binary bytes. Asc() and Chr() are just methods to simplify the human understanding of those values. To intrepret the 'value' of a given byte as an ASCII character use the Asc function (eg strA = Asc(65)) and to return the binary value of a given character use the Chr Function (eg intA = Chr("A") )
If you want to work in Hexadecimal representation you can use the Hex function and &H representation of data (eg Debug.Print Hex(Asc("A")) would print 41 and Debug.Print = Asc(&H41) would print A)

So, if the length of a record is in say element number 3 of your input stream the decimal interpretation of that length would be: intLength = Chr(bytData(3)).

UBound and LBound are most useful and necessary if you are using Dynamic Arrays. Where an array is being populated automatically, as in the MSComm case, you need to know how many bytes have been input. As each byte received is being put into individual elements of the array you can derive the number of bytes read by examining the UBound (Upper Bound) and LBound (Lower Bound) of the array.
eg
Code:
bytArray() = MSComm1.Input intBytesRead = UBound(bytArray) - LBound(bytArray) + 1
ReDim and ReDim Preserve are used to change the dimensions of the array dynamically. (The difference between the two is, as implied, using the 'Preserve' keyword preserves the existing contents of the array whereas ReDim by its own destroys the existing contents of the array)
eg
Code:
ReDim Preserve bytArray(UBound(btyArray) + 1)
would increase the the number of elements in bytArray by 1
and
Code:
ReDim bytArray(0)
would effectively destroy the contents of bytArray

It's not too difficult once you get your mind around it

Regards
Doug
__________________
semel insanivimus omnes
S Data in context = Information, S Information in context = Knowledge, S Knowledge in context = Experience
S Experience in context = Wisdom= Data

Last edited by DougT; 06-28-2006 at 02:27 AM. Reason: Removed the word 'packet'
Reply With Quote
  #3  
Old 06-28-2006, 08:26 AM
fredy989q fredy989q is offline
Regular
 
Join Date: Sep 2004
Posts: 57
Default

Hi, especially to DOugT.

I chuckled when you suggested I was using the MSComm control in anger! I am angry not with the control but with myself for not being able to figure it all out.

The PROTOCOL for this client instrument is really not as crazy as it may sound. Judging from its size - it has to be an embedded micro with ROM and RAM. The client only responds to queries from my host. It does not originate any dialog. The host queries request certain responses but if the request contains errors as received (unrecognized packet type, bad checksum, or incorrect packet length) the client will respond with a simple 7-byte "Error" packet describing the error. A few other rules govern this behaviour.

Thus, I will receive a packet only when one is requested. The return packet type is part of the request but the reply needs to be examined asthe reply packet length can vary depending on the client's database state.

In general, the first byte of a query is a null and the second byte is the packet type. 0 or more "data" bytes follow; the quantity is fixed for each query packet type. This is followed by the XOR of the preceeding bytes and a vbCr.

The client reply is quite similar but generally has many more data bytes, varying in length from just a very few to maybe a hundred or so depending, again, on packet type and client database contents (e.g. whether or not certain tests have been performed. Given the content of each packet's bytes it is fairly easy to identify the checksum byte and the following vbCR. Note that there will be no more traffice from the client at that point (until or unless the host sends another query).

Doug, I believe you touched upon a couple of my problems by mentioning that there have been reports of multiple bytes collected during a receive event even though only single bytes were expected because the RThreshold had been set to 1. It is also important for me to note that when receivng in comInputModeBinary that the byte array is dimensioned autmatically by the MScomm control; so all I need to do is examine its bounds.

I will focus today on dealing with binary mode and see if I can tame it down. I will post my success or failure.

Last edited by fredy989q; 06-28-2006 at 08:29 AM. Reason: Typographical error
Reply With Quote
  #4  
Old 06-29-2006, 11:16 AM
fredy989q fredy989q is offline
Regular
 
Join Date: Sep 2004
Posts: 57
Default Eurika!

I had to give up trying to parse during the OnComm interrupts. I need to use high baud rates and the errors were just not manageable. But I have managed to produce a working solution:

I invented (?) a "retriggerable one-shot" using a Timer control set for 35 milliseconds. Every OnComm interrupt disables and re-enables the timer thus preventing the timer event until there is a delay in the data stream. This works fine within the protocol specs since the client only replies after being polled by the host. I put this in place on both apps (Host and Client). I am using Binary Mode and InputLen=0 and only capture the stream when the timer fires. I then parse the resulting byte array at my leasure.

I am testing at 115200 baud and all seems fine (the target rate is half that).

At this point I suspect that the MSComm control is not well suited to on-the-fly parsing.

I realize that this scheme will be helpful only for certain situations but that works for me.
Reply With Quote
Reply


Currently Active Users Viewing This Thread: 1 (0 members and 1 guests)
 
Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off

Forum Jump

Advertisement:





Free Publications
The ASP.NET 2.0 Anthology
101 Essential Tips, Tricks & Hacks - Free 156 Page Preview. Learn the most practical features and best approaches for ASP.NET.
subscribe
Programmers Heaven C# School Book -Free 338 Page eBook
The Programmers Heaven C# School book covers the .NET framework and the C# language.
subscribe
Build Your Own ASP.NET 3.5 Web Site Using C# & VB, 3rd Edition - Free 219 Page Preview!
This comprehensive step-by-step guide will help get your database-driven ASP.NET web site up and running in no time..
subscribe
More questions on logging Comm data
More questions on logging Comm data
More questions on logging Comm data More questions on logging Comm data
More questions on logging Comm data
More questions on logging Comm data
More questions on logging Comm data More questions on logging Comm data More questions on logging Comm data More questions on logging Comm data More questions on logging Comm data More questions on logging Comm data More questions on logging Comm data
More questions on logging Comm data
More questions on logging Comm data
 
More questions on logging Comm data
More questions on logging Comm data
 
-->