LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

visa read buffer extra byte problem

Solved!
Go to solution

Hi all

I have a problem with visa read. I am reading 566 bytes with start frame 0xCCCC by Labview. some times Labview shows 3 0xCC bytes I mean 0xCCCCCC (on data1 display) what is the problem?

I have checked my data on terminal (with other softwares) there is no extra CC byte and micro works correctly on the other side

could it be for high baud rate?

I have attached my VI

Thanks

Regards

0 Kudos
Message 1 of 22
(3,138 Views)

Does your Instrument output "human-readable messages", i.e. text strings, terminated by <CR><LF>, or does it output binary data encoded somehow, with, say, a byte or bit pattern that signals "end of data stream"? 

 

Almost all modern VISA devices output text, in which case you need to respect that, enable the use of the Termination Character (change the "F" to a "T" in Configure VISA), and read with a Byte Count of 1000 or 1024 (depends if you like Decimal or Binary) and largely ignore Bytes Read.  This gets discussed here on the Forums several times a month.

 

Bob Schor

Message 2 of 22
(3,115 Views)

For reference, Laian had posted this question at the end of this long thread. 

 

visa serial interrupt

Message 3 of 22
(3,110 Views)

not human readable just simple binary data. I dont know the problem really confused why in read buffer some times there is more start frame?

I have changed the start frame to 0xABCD.

Look at my log when the problem occurs more or less after 10 cycles

"ABCD CD00 ...0055 55AB CDAB CD"

you can see there is extra CD in read buffer which causes mess in my table

Download All
0 Kudos
Message 4 of 22
(3,103 Views)

There are lots of things wrong with this. Here are just a few.

 

1. Why are you using a local of Sum of Cluster? There's no guarantee that Sum of Cluster will be calculated before you loop starts. Use a wire.

 

2. Why are you using a local variable for Variable Cluster? Right click on the terminal and select Change to Indicator. You can then wire directly to the terminal.

 

3. I'm not an expert on channel wires, but I don't think that it works the way that you think it works. Channel wires are for transferring data between parallel loops. Move the Main Stop inside your inner loop and pass it's value out to your outer loop.

 

4. Use the terminal for end of read inside the loop. 

 

5. Wires should run from left to right. When you have wires running backward it becomes more difficult to read. If you can use Clean Up Diagram and the program looks better then you're doing something wrong (it looks much better for your program).

 

I suspect that number 1 above may be your culprit, but I'm not sure.

 

 

Message 5 of 22
(3,088 Views)

and also none of my stop button works!

main stop dosent stop the run execution. why?☹️

0 Kudos
Message 6 of 22
(3,076 Views)

You have a dataflow problem.  A while loop inside a while loop.  The main stop is read on the first iteration of the while loop.  It isn't read again, until the 2nd iteration.  But it never gets to the 2nd iteration because the inner while loop will run forever.  Or until sum of cluster equals the number of bytes read.

 

There is no reason for a channel wire in your application.

Message 7 of 22
(3,067 Views)

Hi johntrich

I have done the same as you said and attached my VI here. but just one thing what do you mean for number 4 .

4. Use the terminal for end of read inside the loop. 

I didnt understand can you explain more?

Thanks

0 Kudos
Message 8 of 22
(3,054 Views)

First of all this is very different that what you had before. You need to really consider a better architecture. I would recommend reading up on state machines as I believe this would be very beneficial for your application. In the state machine everything would be done in exactly 1 while loop. You also have a lot of duplicate code. Consider putting this code into a subvi.

 

I don't at all understand what you're trying to do with start frame. The string will always be ABCD even if there were 1000 reads before that. 

 

As for my item in the previous post, in the previous example you were initializing end of read outside the loop and then using a local variable inside the loop. I was suggesting that you do that opposite.

Message 9 of 22
(3,041 Views)

Well, I have a well-deserved reputation for being a Channel Wire Enthusiast, and I see nothing wrong with your using a Tag Channel to have one Stop button stop multiple loops -- much better (in my opinion) to using a Local Variable where the Data Flow is (to be kind) "mysterious".

 

What I think is the problem is those awful Giganta-Clusters, apparently to avoid writing a proper Parser for your Byte Stream from the VISA device.  We (or at least, I) haven't seen the manual for your Device, but from other VISA devices that produced Binary streams that I've used, there were defined "patterns" to the Bytes, sometimes with bits being reserved for "Start of Frame" (or something like that) and ways you could tell if you "missed a Byte" or lost track of where you were.

 

It does look like this might be happening.  We also don't know much about the I/O settings for this device.  I could well imagine that if you are sending "really fast" (like Mega-Baud), have a fairly small buffer for VISA to DMA into, and your code is doing "too much" inside the VISA-reading loop (so that you miss a Byte coming in), you could have problems. 

 

Ah!  I just found a potential Big Problem -- get rid of the VISA Clr inside your data-reading Loop!  You might be throwing away bytes and getting yourself "off track"!

 

I recommend that you structure your VISA Acquisition using a Producer/Consumer Design.  Start by configuring the VISA to have a fairly short Timeout (maybe 100 msec).  The Producer reads some convenient number of Bytes (this will be determined by what the Manual says to expect, but it can also be set more-or-less arbitrary, say at 20).  If there are 20 Bytes there, it puts them into a Channel Stream and sends them to the Consumer loop.  If it Times Out, it will generate an Error, which you "trap" and look at how many bytes were read.  if 0, then you decide if this is a normal "Pause" (again, I have no idea how your device is supposed to work, but it might well be set to "Send 3421 Byte Packets once every 4 seconds", and you'd have a gap between bytes).  Otherwise, you've got a "short Packet", which you can simply send to the Consumer.  You would clear the Error in any case.

 

Your Consumer now becomes a "Parsing State Machine", interpreting the Byte Stream according to the Rules of your Device.  Let the Parser figure out if it should be getting 16-bit, 32-bit, single Byte, or other types of data, and let it assemble the Bytes into the Data Structure that it is supposed to represent.  Here, according to the Parsing Rules specified by your Device, you should be able to see an unambiguous "End of Byte Stream" signal.

 

Note that by creating a Producer/Consumer process, you can use the Channel Stream (or, alternatively, the Byte Queue) to "buffer" the bytes coming in from your device, ensuring that you are (almost-)always reading the data as they come in (and thus not missing any bytes) and have a flexible (expandable) Data Structure to buffer them so you can process them all.

 

Bob Schor

Message 10 of 22
(3,037 Views)