TIA Probleme mit Datenspeicherung von Variablen in 2 DBs. Adressregister?

DennisBerger

Level-2
Beiträge
436
Reaktionspunkte
61
Zuviel Werbung?
-> Hier kostenlos registrieren
Hallo,
wir haben eine Doppelanlage welche rechts und links gleichzeitig Datenwerte (900stk) in 2 getrennte DB_links_kurve und DB_rechts_kurve während einem Prüfablauf ablegen soll.

Die beiden Datensammel FBs für links und rechts werden zyklisch durch OB35 alle 100ms gleichzeitig abgearbeitet.. so dass wir alle 100ms einen Wert speichern.

screenshot OB35:
1690922582349.png


Wenn nur eine Prüfseite läuft, funktioniert alles super.
aber sobald beide Prüfseiten der Anlage gleichzeitig laufen und daten sammeln,
werden teilweise die Werte von der einen Seite im Datenbaustein der anderen Seite gespeichert..


ich vermute mal es hat was mit dem Adressregister zu tun oder? AR1?
hier mal der code für links

FB_links_Kurve:

Code:
L     "DB_links_Kurve".links_Index_Kurve

      L     900
      <=I
      A     "DB_links_Verwaltung".links_Pruefung_laeuft
      JCN   AAAA

      L     "DB_links_Kurve".links_Index_Kurve
      L     4
      *I
      ITD
      SLD   3
      T     #index
      LAR1  #index

      OPN   "DB_links_Kurve"
      L     #links_Pruefdruck_Ist
      T DBD [ AR1 , P#0.0 ]

      L     #links_Tiefdruck_Ist
      T DBD [ AR1 , P#3600.0 ]

      L     #links_Leckdruck_Ist
      T DBD [ AR1 , P#7200.0 ]

      A     "DB_links_Verwaltung".links_Pruefung_laeuft
      JCN   AAAA

      L     "DB_links_Kurve".links_Index_Kurve
      L     1
      +I
      T     "DB_links_Kurve".links_Index_Kurve


und hier für rechts:

FB_rechts_Kurve:

Code:
L     "DB_rechts_Kurve".rechts_Index_Kurve
      L     900
      <=I
      A     "DB_rechts_Verwaltung".rechts_Pruefung_laeuft
      JCN   AAAA

      L     "DB_rechts_Kurve".rechts_Index_Kurve
      L     4
      *I
      ITD
      SLD   3
      T     #index
      LAR1  #index

      OPN   "DB_rechts_Kurve"

      L     #rechts_Pruefdruck_Ist
      T DBD [ AR1 , P#0.0 ]

      L     #rechts_Tiefdruck_Ist
      T DBD [ AR1 , P#3600.0 ]

      L     #rechts_Leckdruck_Ist

      T DBD [ AR1 , P#7200.0 ]

      A     "DB_rechts_Verwaltung".rechts_Pruefung_laeuft
      JCN   AAAA

      L     "DB_rechts_Kurve".rechts_Index_Kurve
      L     1
      +I
      T     "DB_rechts_Kurve".rechts_Index_Kurve


DB_rechts_kurve:
1690922120714.png

DB_links_Kurve
1690922214943.png

hier sollen die Werte gespeichert werden für die jeweilige Seite
____________________________

Tia V16
CPU S7-1513

jemand ne Idee was da falsch läuft? bzw wie man das Problem lösen kann?

danke für Tipps
 
Zuletzt bearbeitet:
Der Code sieht auf die schnelle richtig, aber nicht zeitgemäß aus. Ich vermute die Werte sind schon falsch in #links_ und #rechts_. Wo kommen die Variablen her?

Ist der Code migriert? Sowas könnte man herrlich in SCL vollsymbolisch programmieren und die Arrays als Parameter übergeben. Da bräuchte man auch keine getrennten FBs.
 
Zuviel Werbung?
-> Hier kostenlos registrieren
die Variablenwerte werden weiter oben in den beiden FBs übergeben.

hier mal screenshots aus FB_linke_Kurve:
1690924180511.png
1690924223773.png

usw

das gleiche gibt es dann im FB_rechte_Kurve



ich weiss, dass es sicherlich auch in SCL geht, aber den obigen Code habe ich aus einer anderen Anlage mit nur einer Prüfseite so übernommen,
SCL kann ich das leider aufgrund mangelnden Kenntnissen nicht umsetzen..
auch fehlt mir die Zeit dazu..

dachte hier hat jemand ne Lösung die mit dem o.g. Code geht..

Die Variablenwerte stimmen.. funktioniert ja auch solange nur eine Seite der Prüfung läuft also (linke Kurve oder rechte Kurve daten sammelt)

ich vermute mal es liegt daran, dass Werte im gleichen Adressspeicher AR1 und P#adresse liegen , beide FBs gleichzeitig aufgerufen werden durch OB35 und somit willkürlich gespeichert werden.
kann das sein?

Leider kann ich keine arrays größer 10000 machen, dann meckert nämlich Tia (offset zu gross)
sonst hätte ich die linke seite von 0.0. bis 7200
und die rechte seite zb ab 10840 gestartet.
siehe:
1690925003281.png


die linken Werte in AR1 und die rechte Seite in AR2 speichern geht nicht oder?
 
Zuletzt bearbeitet:
Mir ist was eingefallen:
wie arbeitet Siemens die Bausteine aus dem OB 35 ab? einen nach dem anderen
also OB35 -> FB_rechts_Kurve -> FB_links_Kurve?
so hab ich es doch im kopf, oder bin ich falsch?


Oder gleichzeitig bzw parallel?
OB35 -------- FB_links_Kurve
I
------ FB_rechts_Kurve
1690926962924.png

wenn nacheinander dürft es ja kein Problem mit dem AR1 geben oder?


Ich habe oben die 3 Variablen von Temp auf Static geändert, nun scheint es zu gehen?


vorher:
1690926787402.png
nachher:
1690926745987.png


kann das schon der Fehler gewesen sein, dass die 3 Variablen als temp abgelegt waren?
 
das gleiche gibt es dann im FB_rechte_Kurve
(...)
den obigen Code habe ich aus einer anderen Anlage mit nur einer Prüfseite so übernommen
Da wirst Du wohl nach dem Baustein-Kopieren und -Anpassen noch irgendwo einen Fehler drin haben? Wir sehen ja nicht den ganzen Code... Du müsstest uns schon den ganzen Code von FB19 und FB25 zeigen.

Ich vermute, die Ursache Deines Problems liegt nicht in dem gezeigten Code.
Der Stil der Programmierung ist allerdings nicht nur altertümlich, sonder auch recht eigentümlich. Z.B. für mich ist unverständlich, warum im FB der eigene IDB als Global-DB geöffnet wird und auf IDB-Variablen vollqualifiziert zugegriffen wird (z.B. auf #rechts_Index_Kurve) Wollte da jemand, daß die FB-internen Zugriffe auf die lokalen Static-Variablen in den globalen Querverweisen auftauchen? Oder der ursprüngliche Programmierer konnte es halt nicht besser und wußte nicht, daß man auf den IDB mit "T DID [...]" zugreift? Und die Anwender des Codes haben den Code anscheinend auch nie genau angesehen oder nicht verstanden.

SCL kann ich das leider aufgrund mangelnden Kenntnissen nicht umsetzen..
auch fehlt mir die Zeit dazu..
Ja, "fehlt mir die Zeit" ist meistens das Argument, daß 30 Jahre alter Code über 3 Steuerungsfamilien nahezu unverändert übernommen wird, inklusive der Fehler... und niemand versteht den Code...

dachte hier hat jemand ne Lösung die mit dem o.g. Code geht..
Wozu Eure Programmierer in Jahrzehnten "keine Zeit" hatten, soll hier jemand richtigen Code "aus dem Ärmel schütteln"? ;)
Du hast aber Glück - der in Beitrag #1 gezeigte AWL-Code-Schnippsel läßt sich in ein paar Zeilen SCL-Code übersetzen.
(SCL, ungetestet):
Code:
IF #rechts_Index_Kurve < 900 AND "DB_rechts_Verwaltung".rechts_Pruefung_laeuft THEN
    #rechts_Prufdruck_Speicher[#rechts_Index_Kurve] := #rechts_Pruefdruck_Ist;
    #rechts_Tiefdruck_Speicher[#rechts_Index_Kurve] := #rechts_Tiefdruck_Ist;
    #rechts_Leckdruck_Speicher[#rechts_Index_Kurve] := #rechts_Leckdruck_Ist;
    #rechts_Index_Kurve += 1;
END_IF;


Die Variablenwerte stimmen.. funktioniert ja auch solange nur eine Seite der Prüfung läuft also (linke Kurve oder rechte Kurve daten sammelt)
Die Ursache des Fehlers liegt vermutlich nicht in dem in Beitrag #1 gezeigten Code. Da sehe ich nur die Fehler, daß der Index auf <= 900 geprüft wird: <=I ist falsch, es muß <I lauten. (Und irgendwo muß der Index mal auf 0 gesetzt werden, das hast Du uns nicht gezeigt.)
Wird womöglich von außerhalb der FB ebenso altertümlich-"kunstvoll" in die IDB geschrieben?

Leider kann ich keine arrays größer 10000 machen, dann meckert nämlich Tia (offset zu gross)
sonst hätte ich die linke seite von 0.0. bis 7200
und die rechte seite zb ab 10840 gestartet.
siehe:
Anhang anzeigen 70481
In SCL braucht man auf solche Details nicht achten. :cool:

die linken Werte in AR1 und die rechte Seite in AR2 speichern geht nicht oder?
In FB darf der Inhalt des AR2 nicht verändert werden, besonders wenn man nicht weiß, was man tut.

ich vermute mal es liegt daran, dass Werte im gleichen Adressspeicher AR1 und P#adresse liegen , beide FBs gleichzeitig aufgerufen werden durch OB35 und somit willkürlich gespeichert werden.
wie arbeitet Siemens die Bausteine aus dem OB 35 ab? einen nach dem anderen
also OB35 -> FB_rechts_Kurve -> FB_links_Kurve?
so hab ich es doch im kopf, oder bin ich falsch?


Oder gleichzeitig bzw parallel?
OB35 -------- FB_links_Kurve
I
------ FB_rechts_Kurve
Anhang anzeigen 70484

wenn nacheinander dürft es ja kein Problem mit dem AR1 geben oder?
Selbstverständlich werden die Bausteine nacheinander abgearbeitet. Bausteine können gar nicht gleichzeitig abgearbeitet werden. Auch nicht im OB35. Bausteine können sich gegenseitig unterbrechen, aber auch da kommen sich die Werte in AR1 nicht in die Quere.

Ich habe oben die 3 Variablen von Temp auf Static geändert, nun scheint es zu gehen?


vorher:
Anhang anzeigen 70483
nachher:
Anhang anzeigen 70482


kann das schon der Fehler gewesen sein, dass die 3 Variablen als temp abgelegt waren?
Solange der Kopier-Code von Beitrag #1 erst nach den Netzwerken mit dem Laden der Meßwerte in die TEMP-Variablen ausgeführt wird, dürfen die Variablen in TEMP liegen und Deine Änderung dürfte keinen Einfluß haben. Oder wird bei Dir erst aus TEMP in die Arrays kopiert und erst danach die Messwerte nach TEMP kopiert? Das würde erklären, wenn im FB25 (linke Kurve) die Daten der rechten Kurve geschrieben werden. Die Lösung in dem Fall ist aber nicht, die Variablen von TEMP nach Static zu verschieben, sondern die Abarbeitungsreihenfolge der Codeteile zu ändern. (der Code der ganzen Bausteine wäre interessant)

Du änderst einfach planlos, ohne zu begreifen was Du tust! Wegen der uralten indirekten Adressierung der Absolut-Adressen der Arrays im IDB dürfen vor den Arrays keine anderen Variablen eingefügt werden, die Arrays dürfen sich nicht verschieben. Die DB müssen Standard-Zugriff haben und dürfen nicht als Multiinstanz verwendet werden. Solange der gezeigte AWL-Code verwendet wird.

Harald
 
Zuletzt bearbeitet:
Zuviel Werbung?
-> Hier kostenlos registrieren
Temp Variablen sollten immer initialisiert werden, da noch Datenreste in den Speicherbereichen (Gerade bei Offset Adressierung) liegen könnten. Ebenfalls kann die Abarbeitungsreihenfolge auch innerhalb des Blocks problematisch sein.
 
wow, erstmal danke für die guten und langen Antworten..

hier mal der Code vom Löschen bzw Index auf 0 setzen
Code:
      O     "DB_rechts_Verwaltung".Standard_Takt[1]
      JCN   AAAB

      L     0.0
      T     #Null_real

      CALL  FILL
         ptr_type:=Variant
         BVAL    :=#Null_real
         RET_VAL :=#Ret_Val_SFC
         BLK     :="DB_rechts_Kurve".rechts_Prufdruk_Speicher

      O     "DB_rechts_Verwaltung".Standard_Takt[1]
        CALL  FILL
         ptr_type:=Variant
         BVAL    :=#Null_real
         RET_VAL :=#Ret_Val_SFC
         BLK     :="DB_rechts_Kurve".rechts_Tiefdruck_Speicher

      O     "DB_rechts_Verwaltung".Standard_Takt[1]
      CALL  FILL
         ptr_type:=Variant
         BVAL    :=#Null_real
         RET_VAL :=#Ret_Val_SFC
         BLK     :="DB_rechts_Kurve".rechts_Leckdruck_Speicher

AAAB: NOP 0

hier wird der Index im Takt 1 auf 0 geladen
1690985511134.png

Solange der Kopier-Code von Beitrag #1 erst nach den Netzwerken mit dem Laden der Meßwerte in die TEMP-Variablen ausgeführt wird, dürfen die Variablen in TEMP liegen und Deine Änderung dürfte keinen Einfluß haben. Oder wird bei Dir erst aus TEMP in die Arrays kopiert und erst danach die Messwerte nach TEMP kopiert?

Die Werte werden zuerst oben im FB in die #temp Variablen kopiert und dann in den folgenden NWn mit dem awl code in die arrays kopiert.

Wegen der uralten indirekten Adressierung der Absolut-Adressen der Arrays im IDB dürfen vor den Arrays keine anderen Variablen eingefügt werden, die Arrays dürfen sich nicht verschieben. Die DB müssen Standard-Zugriff haben und dürfen nicht als Multiinstanz verwendet werden. Solange der gezeigte AWL-Code verwendet wird.
die arrays sind im db ganz oben, die Reihenfolge passt, standard zugriff ist vorhanden, keine multiinstanz.

Da sehe ich nur die Fehler, daß der Index auf <= 900 geprüft wird: <=I ist falsch, es muß <I lauten.
warum muss es <I sein und nicht <=I?
 
Zuletzt bearbeitet:
Sorry für meinen Einwand und Danke an Harald und Ralf. Jetzt ist endlich bei mir der Groschen gefallen. JCN und OPN hatte ich ja richtig als englische Mnemonik erkannt, aber auf das A war ich voll hereingefallen, da mich der symbolische Name (beginnend mit DB) hinter den A's auf DatenBaustein als Operand fixiert hatte. :oops:
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Da sehe ich nur die Fehler, daß der Index auf <= 900 geprüft wird: <=I ist falsch, es muß <I lauten.
warum muss es <I sein und nicht <=I?

Weil der AWL-Code die theoretische Adresse von Array-Elementen mit Index 900 ausrechnen und drauf zugreifen kann, die Arrays sind aber alle nur "Array [0..899] of Real" - da überschreibt der Code kurzerhand die nachfolgenden Variablen...

Harald
 
Zurück
Oben