-> Hier kostenlos registrieren
Hallo zusammen,
ich möchte ein altes Projekt aus einer 300´ter in einer 1500 ändern. Da ja in der 1500'ter AWL nicht mehr wirklich zeitgemäß ist, soll es angepasst werden. Leider kenne ich mich mit AWL nicht so recht aus und komme hier an meine grenzen. Mein erster Gedanke ist es in SCL und einer Mischung mit FUP zu realisieren. Die Daten in den DB mit einer FOR schleife bei jedem Takt zuschreiben ist einfach. In dem Schieberegister sind die Werte /Tag (1440 min =24 Stunden) vorhanden. Jetzt fehlt mir nur der faden um die Daten wieder passend aus der schleife zu lesen. Die schleife hatte ich mir gedacht, damit die ersten Werte im DB ja auch die letzten sind die eingeschrieben werden, und somit das auslesen für den Kurzzeitwert einfacher ist. Mir gelingt aber das auslesen nicht wirklich... im Anhang mal das Original
FUNCTION_BLOCK "DAY"
TITLE = Bearbeitung des Tagesspeichers mit 1440 Werten
{ S7_Optimized_Access := 'FALSE' }
AUTHOR : Wandt
FAMILY : Anwender
NAME : DAY_MEM
VERSION : 1.0
VAR_INPUT
MENGE : Real; // Mengenwert pro Minute
TAKT : Bool; // Minutentakt
RESET : Bool; // KZW zurücksetzen
ZEIT : Int; // Zeitvorgabe KZW
END_VAR
VAR_OUTPUT
ZEIGER : Int; // interner Speicher-Pointer Umlaufspeicher
ANZ_KZW : Int; // Anzahl Werte für KZW
ANZ_GES : Int; // Anzahl Werte für Tagesspeicher
KZW : Real; // Kurzzeitwert (Menge)
h24 : Real; // 24h-Wert (Menge)
KZW_VOLL : Bool; // Anzahl KZW = SOLL
h24_VOLL : Bool; // Anzahl 24h = 1440
END_VAR
VAR
MEMORY { S7_SetPoint := 'False'} : "Tagespeicher"; // Bereich des Umlaufspeichers
END_VAR
VAR_TEMP
AR1_ALT : DWord; // Hilfsregister AR1
AR2_ALT : DWord; // Hilfsregister AR2
ZAEHLER : Int; // Hilfszähler für Schleifenbearbeitung
H_ZEIGER : Int; // Hilfszeiger für Schleifenbearbeitung
END_VAR
BEGIN
NETWORK
TITLE = Allgemein
U #RESET ;// Reset ?
SPB RESE;
UN #TAKT ;// keine Takt-Signal ?
BEB;
STRT: TAR1 #AR1_ALT ;// AR1 retten
TAR2 #AR2_ALT ;// AR2 retten
NETWORK
TITLE = Pointer berechnen
L 1440;
L #ZEIGER ;// Pointer auf Speicherzelle
>I ;// Letzte Zelle noch nicht beschrieben ?
SPB goon;
L 0 ;// Pointer löschen
goon: + 1 ;// Pointerwert + 1
T #ZEIGER ;// -> Pointer
L 4;
*I ;// Pointer * 4
+ 20 ;// + Offset Speicherbeginn
SLW 3 ;// -> Pointerformat
TAR2 ;// AR2 -> Akku 1
+D ;// AR2 + Pointer
LAR1 ;// -> AR1
L #ANZ_GES;
+ 1 ;// Anzahl gesamt + 1
T #ANZ_GES;
L 1440 ;// Soll = 1440
<I ;// 1440 Werte erreicht ?
SPB AnzK;
S #h24_VOLL ;// -> Meldung 1440 Werte erreicht
T #ANZ_GES ;// Anzahl gesamt auf 1440 begrenzen
AnzK: L #ANZ_KZW;
+ 1 ;// Anzahl KZW + 1
T #ANZ_KZW;
L #ZEIT ;// Vorgabezeit
<I ;// vorgegebene Anzahl erreicht ?
SPB nw3;
S #KZW_VOLL ;// -> Meldung Anzahl Kurzzeitwerte erreicht
L 1;
<I;
SPB Eint;
TAK;
Eint: T #ANZ_KZW ;// Anzahl KZW auf Vorgabe begrenzen
NETWORK
TITLE = Wert eintragen
nw3: L #MENGE ;// aktueller Mengenwert
T DID[ AR1, P#0.0] ;// -> Ringspeicher eintragen
NETWORK
TITLE = KZW aus der Summe der letzten n Werte berechnen (ANZ_KZW)
L 0.0;
T #KZW ;// KZW löschen
L #ZEIGER;
T #H_ZEIGER ;// Zeiger -> Hilfszeiger
L #ANZ_KZW ;// Vorbelegung Anzahl Durchläufe
SCHL1: T #ZAEHLER ;// Zähler aktualisieren
L DID[ AR1, P#0.0] ;// Wert aus Ringspeicher laden
L #KZW;
+R ;// zu KZW addieren
T #KZW ;// Summe in KZW ablegen
L #H_ZEIGER;
+ -1 ;// Hilfszeiger - 1
T #H_ZEIGER;
L 0;
>I ;// Hilfszeiger = 0 ?
SPB PNTR1;
L 1440;
T #H_ZEIGER ;// Hilfszeiger -> Speicherende
PNTR1: L #H_ZEIGER;
L 4;
*I ;// Hilfszeiger * 4
+ 20 ;// + Offset Speicherbeginn
SLW 3 ;// -> Pointerformat
TAR2 ;// AR2 -> Akku 1
+D ;// AR2 + Pointer
LAR1 ;// -> AR1
L #ZAEHLER ;// Zaehler -> Akku 1
LOOP SCHL1 ;// Akku 1 dekrementieren und Sprung
NETWORK
TITLE =
L #ZEIGER ;// Pointer laden
L 4;
*I ;// Pointer * 4
+ 20 ;// + Offset Speicherbeginn
SLW 3 ;// -> Pointerformat
TAR2 ;// AR2 -> Akku 1
+D ;// AR2 + Pointer
LAR1 ;// -> AR1
L 0.0;
T #h24 ;// 24h-Wert löschen
L #ZEIGER;
T #H_ZEIGER ;// Zeiger -> Hilfszeiger
L #ANZ_GES ;// Vorbelegung Anzahl Durchläufe
SCHL: T #ZAEHLER ;// Zähler aktualisieren
L DID[ AR1, P#0.0] ;// Wert aus Ringspeicher laden
L #h24;
+R ;// zu 24h-Wert addieren
T #h24 ;// Summe in 24h-Wert ablegen
L #H_ZEIGER;
+ -1 ;// Hilfszeiger - 1
T #H_ZEIGER;
L 0;
>I ;// Hilfszeiger = 0 ?
SPB PNTR2;
L 1440;
T #H_ZEIGER ;// Hilfszeiger -> Speicherende
PNTR2: L #H_ZEIGER;
L 4;
*I ;// Hilfszeiger * 4
+ 20 ;// + Offset Speicherbeginn
SLW 3 ;// -> Pointerformat
TAR2 ;// AR2 -> Akku 1
+D ;// AR2 + Pointer
LAR1 ;// -> AR1
L #ZAEHLER ;// Zaehler -> Akku 1
LOOP SCHL ;// Akku 1 dekrementieren und Sprung
LAR1 #AR1_ALT ;// AR1 zurückschreiben
LAR2 #AR2_ALT ;// AR2 zurückschreiben
BE ;// ENDE
NETWORK
TITLE = Anzahl KZW = SOLL
RESE: R #KZW_VOLL ;// Meldung "KZW voll" löschen
R #h24_VOLL ;// Meldung "h24 voll" löschen
L 0;
T #ANZ_KZW ;// Anzahl KZW löschen
T #ANZ_GES ;// Anzahl gesamt löschen
SPA STRT ;// -> Baustein bearbeiten
END_FUNCTION_BLOCK
ich möchte ein altes Projekt aus einer 300´ter in einer 1500 ändern. Da ja in der 1500'ter AWL nicht mehr wirklich zeitgemäß ist, soll es angepasst werden. Leider kenne ich mich mit AWL nicht so recht aus und komme hier an meine grenzen. Mein erster Gedanke ist es in SCL und einer Mischung mit FUP zu realisieren. Die Daten in den DB mit einer FOR schleife bei jedem Takt zuschreiben ist einfach. In dem Schieberegister sind die Werte /Tag (1440 min =24 Stunden) vorhanden. Jetzt fehlt mir nur der faden um die Daten wieder passend aus der schleife zu lesen. Die schleife hatte ich mir gedacht, damit die ersten Werte im DB ja auch die letzten sind die eingeschrieben werden, und somit das auslesen für den Kurzzeitwert einfacher ist. Mir gelingt aber das auslesen nicht wirklich... im Anhang mal das Original
FUNCTION_BLOCK "DAY"
TITLE = Bearbeitung des Tagesspeichers mit 1440 Werten
{ S7_Optimized_Access := 'FALSE' }
AUTHOR : Wandt
FAMILY : Anwender
NAME : DAY_MEM
VERSION : 1.0
VAR_INPUT
MENGE : Real; // Mengenwert pro Minute
TAKT : Bool; // Minutentakt
RESET : Bool; // KZW zurücksetzen
ZEIT : Int; // Zeitvorgabe KZW
END_VAR
VAR_OUTPUT
ZEIGER : Int; // interner Speicher-Pointer Umlaufspeicher
ANZ_KZW : Int; // Anzahl Werte für KZW
ANZ_GES : Int; // Anzahl Werte für Tagesspeicher
KZW : Real; // Kurzzeitwert (Menge)
h24 : Real; // 24h-Wert (Menge)
KZW_VOLL : Bool; // Anzahl KZW = SOLL
h24_VOLL : Bool; // Anzahl 24h = 1440
END_VAR
VAR
MEMORY { S7_SetPoint := 'False'} : "Tagespeicher"; // Bereich des Umlaufspeichers
END_VAR
VAR_TEMP
AR1_ALT : DWord; // Hilfsregister AR1
AR2_ALT : DWord; // Hilfsregister AR2
ZAEHLER : Int; // Hilfszähler für Schleifenbearbeitung
H_ZEIGER : Int; // Hilfszeiger für Schleifenbearbeitung
END_VAR
BEGIN
NETWORK
TITLE = Allgemein
U #RESET ;// Reset ?
SPB RESE;
UN #TAKT ;// keine Takt-Signal ?
BEB;
STRT: TAR1 #AR1_ALT ;// AR1 retten
TAR2 #AR2_ALT ;// AR2 retten
NETWORK
TITLE = Pointer berechnen
L 1440;
L #ZEIGER ;// Pointer auf Speicherzelle
>I ;// Letzte Zelle noch nicht beschrieben ?
SPB goon;
L 0 ;// Pointer löschen
goon: + 1 ;// Pointerwert + 1
T #ZEIGER ;// -> Pointer
L 4;
*I ;// Pointer * 4
+ 20 ;// + Offset Speicherbeginn
SLW 3 ;// -> Pointerformat
TAR2 ;// AR2 -> Akku 1
+D ;// AR2 + Pointer
LAR1 ;// -> AR1
L #ANZ_GES;
+ 1 ;// Anzahl gesamt + 1
T #ANZ_GES;
L 1440 ;// Soll = 1440
<I ;// 1440 Werte erreicht ?
SPB AnzK;
S #h24_VOLL ;// -> Meldung 1440 Werte erreicht
T #ANZ_GES ;// Anzahl gesamt auf 1440 begrenzen
AnzK: L #ANZ_KZW;
+ 1 ;// Anzahl KZW + 1
T #ANZ_KZW;
L #ZEIT ;// Vorgabezeit
<I ;// vorgegebene Anzahl erreicht ?
SPB nw3;
S #KZW_VOLL ;// -> Meldung Anzahl Kurzzeitwerte erreicht
L 1;
<I;
SPB Eint;
TAK;
Eint: T #ANZ_KZW ;// Anzahl KZW auf Vorgabe begrenzen
NETWORK
TITLE = Wert eintragen
nw3: L #MENGE ;// aktueller Mengenwert
T DID[ AR1, P#0.0] ;// -> Ringspeicher eintragen
NETWORK
TITLE = KZW aus der Summe der letzten n Werte berechnen (ANZ_KZW)
L 0.0;
T #KZW ;// KZW löschen
L #ZEIGER;
T #H_ZEIGER ;// Zeiger -> Hilfszeiger
L #ANZ_KZW ;// Vorbelegung Anzahl Durchläufe
SCHL1: T #ZAEHLER ;// Zähler aktualisieren
L DID[ AR1, P#0.0] ;// Wert aus Ringspeicher laden
L #KZW;
+R ;// zu KZW addieren
T #KZW ;// Summe in KZW ablegen
L #H_ZEIGER;
+ -1 ;// Hilfszeiger - 1
T #H_ZEIGER;
L 0;
>I ;// Hilfszeiger = 0 ?
SPB PNTR1;
L 1440;
T #H_ZEIGER ;// Hilfszeiger -> Speicherende
PNTR1: L #H_ZEIGER;
L 4;
*I ;// Hilfszeiger * 4
+ 20 ;// + Offset Speicherbeginn
SLW 3 ;// -> Pointerformat
TAR2 ;// AR2 -> Akku 1
+D ;// AR2 + Pointer
LAR1 ;// -> AR1
L #ZAEHLER ;// Zaehler -> Akku 1
LOOP SCHL1 ;// Akku 1 dekrementieren und Sprung
NETWORK
TITLE =
L #ZEIGER ;// Pointer laden
L 4;
*I ;// Pointer * 4
+ 20 ;// + Offset Speicherbeginn
SLW 3 ;// -> Pointerformat
TAR2 ;// AR2 -> Akku 1
+D ;// AR2 + Pointer
LAR1 ;// -> AR1
L 0.0;
T #h24 ;// 24h-Wert löschen
L #ZEIGER;
T #H_ZEIGER ;// Zeiger -> Hilfszeiger
L #ANZ_GES ;// Vorbelegung Anzahl Durchläufe
SCHL: T #ZAEHLER ;// Zähler aktualisieren
L DID[ AR1, P#0.0] ;// Wert aus Ringspeicher laden
L #h24;
+R ;// zu 24h-Wert addieren
T #h24 ;// Summe in 24h-Wert ablegen
L #H_ZEIGER;
+ -1 ;// Hilfszeiger - 1
T #H_ZEIGER;
L 0;
>I ;// Hilfszeiger = 0 ?
SPB PNTR2;
L 1440;
T #H_ZEIGER ;// Hilfszeiger -> Speicherende
PNTR2: L #H_ZEIGER;
L 4;
*I ;// Hilfszeiger * 4
+ 20 ;// + Offset Speicherbeginn
SLW 3 ;// -> Pointerformat
TAR2 ;// AR2 -> Akku 1
+D ;// AR2 + Pointer
LAR1 ;// -> AR1
L #ZAEHLER ;// Zaehler -> Akku 1
LOOP SCHL ;// Akku 1 dekrementieren und Sprung
LAR1 #AR1_ALT ;// AR1 zurückschreiben
LAR2 #AR2_ALT ;// AR2 zurückschreiben
BE ;// ENDE
NETWORK
TITLE = Anzahl KZW = SOLL
RESE: R #KZW_VOLL ;// Meldung "KZW voll" löschen
R #h24_VOLL ;// Meldung "h24 voll" löschen
L 0;
T #ANZ_KZW ;// Anzahl KZW löschen
T #ANZ_GES ;// Anzahl gesamt löschen
SPA STRT ;// -> Baustein bearbeiten
END_FUNCTION_BLOCK