TIA Flakenauswertung auf einzelne Bits im DWord

bitnarrator

Level-1
Beiträge
1
Reaktionspunkte
0
Zuviel Werbung?
-> Hier kostenlos registrieren
Hallo,

ich bin grade dabei eine Anlage einzurichten, die Störmeldungen der Anlage selber kommen über verschiedene Eingänge oder Merker in die SPS (S7-1511 PN, V2.8).

Diese Eingänge werden in einem FC in einen Datenbaustein geschrieben, am Ende per Oder auf den Störungsmerker.


E0.0 Störung Kompressor -> DB1001.DBX0.0 Störung Kompressor-------
E0.1 Störung Heizung -> DB1001.DBX0.1 Störung Heizung --------------
ODER -> M0.0 Störung

(so ähnlich)

Nun wurde ich gerne das bei jeder neuen Störung die Störungslampe A0.0 blinkt. Dann quittier ich diese, Lampe wechselt auf Dauerleuchten um, behebe die Störung, quittiere erneut, Lampe ist aus. Das funktioniert so weit.

Allerdings soll im Zustand "Lampe leuchtet - Störung nicht behoben" eine neue Störung hinzukommen, die Lampe erneut anfangen zu blinken. Dieses würde ich über Trigger lösen wollen, allerdings hätte ich dann keinen Merker mehr der mir Allgemein sagt "Störung liegt an"...


E0.0 Störung Kompressor -> DB1001.DBX0.0 Störung Kompressor -> PTrig -> ODER -> M0.0 Störung

Nun würde ich gerne das gesamte Double-Word im Datenbaustein (DB1001.DBD0) auf eine positive Flanke abfragen, aber so das es jedesmal eine neue Flanke gibt, sobald irgendein Bit von 0 nach 1 wechselt, mit der Anleitung von hier (https://www.sps-forum.de/faq/30058-flankenauswertung-step7.html) funktioniert das nur wenn ein Bit von 0 nach 1 wechselt, danach nicht mehr.


Gibt es da irgendwie eine möglichkeit, Bei jeglichen Bitwechsel von 0 nach1 im DoubleWord DB1001.DBD0 eine Flanke zu generieren, um so das Blinken der Störungslampe erneut zu triggern?


Oder hab ich da ganz allgemein einen Denkfehler drin??



Danke schonmal und bleibt gesund

Marcel // bitnarrator
 
Hier mal eine kleine Hilfe für steigende und fallende Flanke

Code:
FOR #x := #WORDFELD_START TO #WORDFELD_ENDE DO
  #tmpWordFeld := #WordFeld[#x] XOR #WordFeldFM[#x];
  #WordFeldFP[#x] := #tmpWordFeld AND #WordFeld[#x];
  #WordFeldFN[#x] := #tmpWordFeld AND NOT #WordFeld[#x];
  #WordFeldFM[#x] := #WordFeld[#x];
END_FOR;
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Nun würde ich gerne das gesamte Double-Word im Datenbaustein (DB1001.DBD0) auf eine positive Flanke abfragen, aber so das es jedesmal eine neue Flanke gibt, sobald irgendein Bit von 0 nach 1 wechselt, mit der Anleitung von hier (Flankenauswertung in Step7) funktioniert das nur wenn ein Bit von 0 nach 1 wechselt, danach nicht mehr.

Dann könntest du im Prinzip dein Doppelwort auf Wertänderung überwachen:

DeineFlanke := DeinDoppelwort <> AltWertDeinDoppelwort;

AltWertDeinDoppelwort := DeinDoppelwort;
 
Nun würde ich gerne das gesamte Double-Word im Datenbaustein (DB1001.DBD0) auf eine positive Flanke abfragen, aber so das es jedesmal eine neue Flanke gibt, sobald irgendein Bit von 0 nach 1 wechselt, mit der Anleitung von hier (Flankenauswertung in Step7) funktioniert das nur wenn ein Bit von 0 nach 1 wechselt, danach nicht mehr.
??? Wie "danach nicht mehr"?
Der Code in der FAQ liefert im OUT-Word ein 1-Bit, wenn das zugehörige Bit im IN-Word eine positive Flanke hat. Du brauchst doch nur noch prüfen, ob in dem OUT-Word irgendein Bit gesetzt ist - sprich: ob das Word <> 0 ist.

Wenn aber in einem Zyklus ein Eingang eine Flanke hat und genau im nächsten Zyklus hat ein anderer Eingang eine Flanke, dann ergibt das ein 2 Zyklen langes 1-Signal ohne zwischendurch auf 0 zu gehen. Ist das das Problem was Du meinst?

Code:
FUNCTION "P_FLANKE_D" : VOID
TITLE =positive Flankenerkennung 32 Bit
AUTHOR : PN_DP
VERSION : 0.1

VAR_INPUT
  IN : DWORD ;   //zu untersuchendes DWord
END_VAR
VAR_OUTPUT
  OUTD : DWORD ;  //ErgebnisDword mit den Flanken-Bits
  OUTX : BOOL ;   //Sammelanzeige irgendein Bit hat eine Flanke
END_VAR
VAR_IN_OUT
  HM : DWORD ;   //Hilfsmerker: IN vorher
END_VAR
BEGIN
NETWORK
      L     #IN;
      L     #HM;
      INVD  ;
      UD    ;
      T     #OUTD;
      U     <>0;
      =     #OUTX;
      SAVE;        //falls Ergebnis an ENO gewünscht ist

      L     #IN;
      T     #HM;
END_FUNCTION

Harald
 
Zuviel Werbung?
-> Hier kostenlos registrieren
... aber leider noch nicht perfekt. Der Code könnte zwischen der Verknüpfung für #OUTD und dem Speichern des #IN unterbrochen werden und #IN könnte sich in der Zeit ändern *grrrml*

Besser:
Code:
      L     #HM;
      L     #IN;
      T     #HM;
      TAK   ;
      INVD  ;
      UD    ;
      T     #OUTD;
      U     <>0;
      =     #OUTX;
      SAVE  ;      //Sammelanzeige auch an ENO

Und in TIA SCL:
Code:
    #temp_IN := #IN;
    #temp_OUTD := #temp_IN AND NOT (#HM);  //Ermittlung positive Flanken
    #HM := #temp_IN;

    #P_FLANKE_D := #temp_OUTD;        //ErgebnisDword mit den Flanken-Bits
    ENO := #OUTX := #temp_OUTD <> 0;  //Sammelanzeige irgendein Bit hat eine Flanke

Harald
 
Code:
[LEFT][COLOR=#333333][FONT=Courier]L     #HM;
L     #IN;
T     #HM;
XOD   ;
[/FONT][/COLOR][LEFT][COLOR=#333333][FONT=Courier][COLOR=#333333][FONT=Courier]L     #IN;[/FONT][/COLOR]
[COLOR=#333333][FONT=Courier]UD   ;
[/FONT][/COLOR][/FONT][LEFT][FONT=Courier][COLOR=#333333][FONT=Courier][COLOR=#333333][FONT=Courier]T     #OUT;[/FONT][/COLOR][/FONT][/COLOR] [/FONT][/LEFT]
[/COLOR][/LEFT]
[/LEFT]

Das habe ich so in der Wort-Variante seit 2009 im Einsatz, sollte auch für Doppelwort funktionieren.
 
Das habe ich so in der Wort-Variante seit 2009 im Einsatz, sollte auch für Doppelwort funktionieren.
Funkioniert auch für DoppelWort.
Das zweite L #IN würde ich gegen TAK tauschen, dann wird kein SpeicherZugriff erforderlich für das, was ohnehin noch im Akku steht.
Das Tauschen der Akkus 1 und 2 vor der Ausführung des XOD hat keine Auswirkung auf das Ergebnis des XOD, wohl aber darauf, dass nach XOD der Wert von #IN noch in Akku 2 verfügbar ist.
Code:
L     #HM;
L     #IN;
T     #HM;
TAK   ;
XOD   ;
UD    ;
T     #OUT;
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Das zweite L #IN würde ich gegen TAK tauschen, dann wird kein SpeicherZugriff erforderlich für das, was ohnehin noch im Akku steht.
Der Speicherzugriff ist nicht nur nicht erforderlich, sondern kann auch Probleme bei Multitasking machen.

Code:
L     #HM;
[COLOR="#0000FF"]L     #IN;[/COLOR]
T     #HM;
XOD   ;
[COLOR="#0000FF"]L     #IN;[/COLOR]
UD   ;
T     #OUT;
Das fragt #IN zweimal ab. Das kann Probleme machen, falls IN per Referenz übergeben wird, und der Code zwischen den beiden "L #IN" unterbrochen wird und in der Zeit der an IN verschaltete Wert verändert wird. Z.B.:
Code:
//in OB1-Zyklus
CALL "FC_FLANKE"
 IN :=MD40
 OUT:=MD44
 HM :=MD48


//in OB3x, OB4x, OB8x, .. Alarm-OB
T MD40 //oder MB40..MB43, MW39..MW43, MD37..MD43, oder S/R/= M40.0..M43.7

In der FAQ war es mir wichtig, die allgemeine Arbeitsweise von Flankenerkennungen leicht verständlich zu zeigen. Bei unterbrechungsfest formuliertem Code hätte die Verständlichkeit stark gelitten.
Wenn man Standard-Code/Bausteine für Anwender erstellt (womöglich noch mit KnowHow-Protect), dann sollte der Code aber unter ALLEN Einsatzumständen korrekt funktionieren. Da steht Verständlichkeit nicht mehr an erster Stelle.

Harald
 
Danke für die Erläuterung. Habe ich gleich bei mir angepasst. Habe den Code damals irgendwo von einem S5-Baustein abgeschrieben
;)
 
Zurück
Oben