TIA Array of Byte in DINT umwandeln

Stephan_92

Level-1
Beiträge
26
Reaktionspunkte
1
Zuviel Werbung?
-> Hier kostenlos registrieren
Servus zusammen,

ich habe ein Array of byte und möchte hieraus eine DINT Variable bilden.

ArrayElement[4] bis ArrayElement[7] wären hierfür meine 4 Byte die ich in den DINT wandeln möchte.

Das ganze soll in SCL geschrieben sein.

Ich habe an einen AnyPointer gedacht gehabt allerdings funktioniert das nicht, da ich optimierte Speicherbereiche habe.

Vielen Dank im voraus.

Software ist TIA V15 SP1
 
Moin Stephan,

wenn du auf einer 1200/1500er Steuerung unterwegs bist, dann sollte sich das mit dem Standard-Baustein Deserialisieren realisieren lassen. Der wandelt einen Byte-Stream (sequenzielle Darstellung) in einen beliebigen Datentyp zurück.
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Die "Hand am Arm" Lösung wäre man nutze die Slice Funktion (Falls die CPU Firmware denn "Deserialize" mit optimierten Speicher nicht unterstützt):

Code:
#meine_DINT_Variable.%B0 := #ArrayElement[4];
#meine_DINT_Variable.%B1 := #ArrayElement[5];
#meine_DINT_Variable.%B2 := #ArrayElement[6];
#meine_DINT_Variable.%B3 := #ArrayElement[7];
 
Die zweite Variante mit der SLICE Anweisung wäre mir die liebste, allerdings dürfte die bei REAL-Variablen nicht funktionieren?

DESERIALIZE muss ich mir mal anschauen, da habe ich noch nicht damit gearbeitet.

Auf jedenfall Danke
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Code:
#temp_DWORD_Variable.%B3 := #ArrayElement[4];
#temp_DWORD_Variable.%B2 := #ArrayElement[5];
#temp_DWORD_Variable.%B1 := #ArrayElement[6];
#temp_DWORD_Variable.%B0 := #ArrayElement[7];
#meine_REAL_Variable := DWORD_TO_REAL(#temp_DWORD_Variable);

Harald
 
Code:
#temp_DWORD_Variable.%B3 := #ArrayElement[4];
#temp_DWORD_Variable.%B2 := #ArrayElement[5];
#temp_DWORD_Variable.%B1 := #ArrayElement[6];
#temp_DWORD_Variable.%B0 := #ArrayElement[7];
#meine_REAL_Variable := DWORD_TO_REAL(#temp_DWORD_Variable);

Harald

Aber nur, wenn er eine DINT (Post #1) reinbekommt, ist der Input schon eine Real (Post #4), dann wird die Wandlung in die Hosen gehen, oder?
 
Aber nur, wenn er eine DINT (Post #1) reinbekommt, ist der Input schon eine Real (Post #4), dann wird die Wandlung in die Hosen gehen, oder?

Wenn er doch zuerst von dword in den Datentypen wandelt den das bytearray darstellt und danach in den den er braucht. Dürfte doch alles klar gehen.

Im 1. Post sagt er das Array stellt einen dint dar. Und im 4. will er mit einem real weiterarbeiten.

Ich würd die Bytes in ein Word schieben und auf slice verzichten (dann läufts auf jeder FW und Steuerung) das Wort dann auf den ursprungsdatentyp kopieren. Und dann in den nutzdatentyp Wandeln.


Gesendet von iPhone mit Tapatalk
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Aber nur, wenn er eine DINT (Post #1) reinbekommt, ist der Input schon eine Real (Post #4), dann wird die Wandlung in die Hosen gehen, oder?
Wenn die 4 Bytes die 4 Teile eines originalen REAL sind (z.B. per Kommunikation empfangen) dann funktioniert das Zusammenbasteln. DWORD_TO_* wandelt nicht sondern kopiert die 32 Bit 1:1 in den 32 Bit großen Zieldatentyp.

Stephan_92 hat 2 Fragen gestellt:
(1) im Beitrag #1: 4 Byte zum ursprünglichen DINT zusammenziehen
(2) im Beitrag #4: 4 Byte zum ursprünglichen REAL zusammenziehen

Slice-Anweisungen gehen nur mit Bitstring-Datentypen. Wenn man die IEC-Prüfung ausschaltet darf man auch Ganzzahl-Datentypen slicen.

Deshalb müsste man zunächst die 4 Byte in ein DWORD reinbasteln, und dann das Bitmuster des DWORD 1:1 ohne Veränderung in eine Variable des Ziel-Datentyps kopieren - das macht DWORD_TO_DINT bzw. DWORD_TO_REAL

zu (1) 4 Byte zu DINT:
Code:
#temp_DWORD_Variable.%B3 := #ArrayElement[4];
#temp_DWORD_Variable.%B2 := #ArrayElement[5];
#temp_DWORD_Variable.%B1 := #ArrayElement[6];
#temp_DWORD_Variable.%B0 := #ArrayElement[7];
#meine_DINT_Variable := DWORD_TO_DINT(#temp_DWORD_Variable);
zu (2) 4 Byte zu REAL:
Code:
#temp_DWORD_Variable.%B3 := #ArrayElement[4];
#temp_DWORD_Variable.%B2 := #ArrayElement[5];
#temp_DWORD_Variable.%B1 := #ArrayElement[6];
#temp_DWORD_Variable.%B0 := #ArrayElement[7];
#meine_REAL_Variable := DWORD_TO_REAL(#temp_DWORD_Variable);

Anstatt Slice-Zugriffen könnte man auch per "AT" eine DINT- oder REAL-Variable mit einem 4-Byte-Array überlagern, dann die 4 Bytes hineinspeichern und als DINT oder REAL herauskopieren - das will TIA aber nicht mit "optimiertem" Speicher machen (auch nicht "optimierter" TEMP) sondern nur mit Speicher mit Standard-Zugriff.

Ganz allgemeingültig (aber aufwändiger) kann man auch noch jedes Byte einzeln zu DWORD erweitern und an die richtige Bitposition schieben und alle 4 miteinander verodern.

Harald
 
Anstatt Slice-Zugriffen könnte man auch per "AT" eine DINT- oder REAL-Variable mit einem 4-Byte-Array überlagern, dann die 4 Bytes hineinspeichern und als DINT oder REAL herauskopieren - das will TIA aber nicht mit "optimiertem" Speicher machen (auch nicht "optimierter" TEMP) sondern nur mit Speicher mit Standard-Zugriff.
Ach Harald,
immer wieder behauptest Du das und immer wieder korrigiere ich Dich, dass das im optimierten FB sehr wohl geht, wenn die Remanenz der Variablen auf "im IDB setzen" gestellt wird.
Und es geht natürlich nur mit Variablen, die auch im IDB gespeichert werden. Also alle außer TEMP.
Man könnte also z.B. direkt den Input überlagern, an den Ausgang überweisen und benötigt nicht mal TEMP.
;)

:ROFLMAO:
 
Ach Mario,
ich weiß daß immer von Dir dieser Hinweis kommt. ;)
Ich behaupte einfach mal: Variablen mit dem Attribut "im IDB setzen" liegen nicht in "optimiertem" Speicher - dann hätten wir beide recht.

Harald
 
Also danke für die vielen Antworten,

ich habe mich für SLICE mit DWORD_TO_REAL / DWORD_TO_DINT entschieden.

Der Tempbereich wird in dem Baustein benötigt da, die Daten im Array mehrfach im Baustein benötigt werden.

Auf Variablen die Daten fest verschieben geht nicht oder ist zu aufwändig, da das Array die Daten immer an einer anderen Stelle stehen hat und durch Schleifen dann im Programmablauf über die SLICE Aufrufe verarbeitet wird.

Auf jedenfall danke ;)
Jetzt läuft es
 
Zurück
Oben