Byte Swap a String in Studio5000

EG engineer

Member
Join Date
Oct 2020
Location
Shelby Twp
Posts
5
I have a C-More HMI that changes my PLC String from "Machine Status" to "aMhcni etStasu" .
There is an option with other objects that have string to"Byte Swap" but that option doesnt exsist with a multistate text indicator.

So my question is; What is the best way to byteswap an ascii String in the PLC?

I understand there is a Byte swap instruction(SWPB) but this only works with a integer. And using the String to Dint instruction(STOD) then Dint to String(DTOS) isnt an option because my string only contains ascii characters.

Obviously I could use an A**load of "MID" and "CONCAT" instructions to get there I just feel like there has to be a better way!


I was really starting like like these HMI's before I ran into this issue.🔨




Cheers!
 
A silly brute force way:

MOV MyString.LEN FixedString.LEN
MOV MyString.Data[0] FixedString.Data[1]
MOV MyString.Data[1] FixedString.Data[0]
...

Code:
BST MOV MyString.LEN FixedString.LEN NXB MOV MyString.DATA[0] FixedString.DATA[1] MOV MyString.DATA[1] FixedString.DATA[0] NXB MOV MyString.DATA[2] FixedString.DATA[3] MOV MyString.DATA[3] FixedString.DATA[2] NXB MOV MyString.DATA[4] FixedString.DATA[5] MOV MyString.DATA[5] FixedString.DATA[4] NXB MOV MyString.DATA[6] FixedString.DATA[7] MOV MyString.DATA[7] FixedString.DATA[6] NXB MOV MyString.DATA[8] FixedString.DATA[9] MOV MyString.DATA[9] FixedString.DATA[8] NXB MOV MyString.DATA[10] FixedString.DATA[11] MOV MyString.DATA[11] FixedString.DATA[10] NXB MOV MyString.DATA[12] FixedString.DATA[13] MOV MyString.DATA[13] FixedString.DATA[12] BND

If you have a lot of this going on, you could put it in an AOI.
 
A silly brute force way:

[lots of MOV]

This is the best I could come up with as well.

I've liked what I've seen of the C-More line (I'm in the process of converting some old PV550), but haven't ever tried to embed a string in a multistate indicator so I hadn't come across this.

I don't know why they didn't make the 'byte-swap' option a selection for the tag itself that would apply across the board wherever it is used; I can't think of any reason you'd want to sometimes byte-swap a given string and other times not.
 
This is the best I could come up with as well.

I've liked what I've seen of the C-More line (I'm in the process of converting some old PV550), but haven't ever tried to embed a string in a multistate indicator so I hadn't come across this.

I don't know why they didn't make the 'byte-swap' option a selection for the tag itself that would apply across the board wherever it is used; I can't think of any reason you'd want to sometimes byte-swap a given string and other times not.


I ran into that exact issue trying to embed strings as well. Ended up just not using the built in alarm history and rolled my own in the PLC.


One thing you can do is set up an event in the event manager to read the PLC string into an internal string (you can do byte swapping in events). Then embed the internal string in the multistate indicator. If you have a lot of strings, and a lot of events, though, you will bog down the HMI. You'll also need something to trigger the event (like navigating to that screen).
 
Rung 000 and either rung 0001 or 0002 below (translated to Logix, of course); S is the string. Rung 0001 will not work if Logix does not treat S.DATA[INDEX] as a SINT, but I think Rung 0002 will always work.
Untitled.png
 
Last edited:
A little more dancing outside the loop, a little less in the loop (AEX in 500 is MID in 5000; similar caveats):
Untitled.png
 
Last edited:
... and a little less outside the loop by executing the shift after the loop; this may not work if the string does not have extra space to begin with (e.g. length of 82 or more).
Untitled.png
 
I have a C-More HMI that changes my PLC String from "Machine Status" to "aMhcni etStasu" .
There is an option with other objects that have string to"Byte Swap" but that option doesnt exsist with a multistate text indicator.

So my question is; What is the best way to byteswap an ascii String in the PLC?

I understand there is a Byte swap instruction(SWPB) but this only works with a integer. And using the String to Dint instruction(STOD) then Dint to String(DTOS) isnt an option because my string only contains ascii characters.

Obviously I could use an A**load of "MID" and "CONCAT" instructions to get there I just feel like there has to be a better way!

I was really starting like like these HMI's before I ran into this issue.🔨

Cheers!

Does SWBT not work on the .DATA[] member of the string?
 
Does SWBT not work on the .DATA[] member of the string?

Only DINT/INT/REAL types

Edit: so you'd have to copy the data array into an array of INT's, SWPB each INT, then copy back to the SINT data array. Might as well use my brute force method at that point.
 
Last edited:
Only DINT/INT/REAL types

Edit: so you'd have to copy the data array into an array of INT's, SWPB each INT, then copy back to the SINT data array. Might as well use my brute force method at that point.

Oof.

Can the .LEN member be specified as the beginning of source data, then restored after the swap?
 
Oof.

Can the .LEN member be specified as the beginning of source data, then restored after the swap?

I think I'm following what you are asking. I don't think it matters when up update the LEN member. In my example, I set the LEN of the new string from the source first, then move the data while swapping it. You could handle the data first, then update the length.

Even if I don't update the LEN, so it stays at zero, the data will still be in the data array, it will just display as if the string is empty on a rung.
 
I would look for a means to change the "endianess" byte order of the communications.
Let me guess. You are using Modbus RTU with little endian devices.
Does the PLC have a roll left or roll right instruction? If you roll and word 8 bits in either direction it does the same as a swap.


Close. He's using an Automation Direct C-More HMI that needs byte-swapping enabled. On the C-More end, a lot of the objects support string byte-swapping but not all. It does not support byte swapping at the tag or driver level, which is what I would expect. It's an oversight (a serious one...) on the part of C-More developers.
 
I think I'm following what you are asking. I don't think it matters when up update the LEN member. In my example, I set the LEN of the new string from the source first, then move the data while swapping it. You could handle the data first, then update the length.

Even if I don't update the LEN, so it stays at zero, the data will still be in the data array, it will just display as if the string is empty on a rung.

Right on - by feeding the SWBT a DINT from the same “collection” as the SINTs you might coerce it to work. Side effect being that the DINT would have its bytes swapped so you might have to use a temp DINT to hang onto the original value.

***Or maybe that doesn’t matter since the C-more may have the endianness handled for that anyway. /puzzled
 
Last edited:

Similar Topics

I ran into a situation where some devices I use display String bytes in a swapped order as they are stored in my PLC (CompactLogix). I thought it...
Replies
3
Views
3,851
I am writing software for a system(*) that has the following data flow 4-20mA Sensor => Siemens AI 8xU/I/RTD/TC ST card Siemens AI 8xU/I/RTD/TC...
Replies
16
Views
6,607
Good Morning, I'm using RS Logix 5000 to program an Allen-Bradley 1769-QBFC1B Version 20.12 and want to use the Byte Swap Instruction (SWPB)...
Replies
7
Views
4,962
Hi guys I'm having some weird data conversion issue over modbus happening. And I found a post here before that is similar to what I'm seeing but...
Replies
6
Views
7,187
Hello everybody, I have a communication to a Linux-PC via sockets. So I created a quite large UDT with all the content. Unfortunately we have to...
Replies
1
Views
2,150
Back
Top Bottom