Quantcast
Channel: SPS-Forum - Automatisierung und Elektrotechnik
Viewing all articles
Browse latest Browse all 47324

TIA Bereichslängenfehler SCL

$
0
0
Servus Leute,

wie mein Titel schon sagt bekomme ich einen Bereichslängenfehler in einem SCL Baustein. Ich kann mir leider nicht erklären woher dieser Fehler kommt.
Kurz zur Erklärung:
Der betroffene Baustein prüft einen erhaltenen Fahrauftrag auf plausibilität. Der Fehler taucht auch nicht bei jedem Fahrauftrag auf. Ich hoffe ihr habt vielleicht ne Idee was es sein könnte, oder könnt mir vielleicht helfen wie ich den Fehler diagnostizieren kann.

Hier der Auszug aus dem Diagnosepuffer der CPU

Code:

Diagnosepuffer der Baugruppe Kran1_3100 [CPU 1515F-2 PN]


Artikel-Nr. / Bezeichn.      Komponente                    Version
6ES7 515-2FM01-0AB0          Hardware                      3
- - -                        Firmware                      V 2.0.1
Firmware-Erweiterung          Firmware-Erweiterung          ---



103 von 523; Ereignis-ID: 16# 02:2522
Temporärer CPU-Fehler: Bereichslängenfehler in FB 11
betrifft OB 1 Ausführung
Lesezugriff Gepufferter DB-Bereich
fehlerhafte Adresse, Operand ersetzt
 
 Kran1_3100
interne Adressierungsdetails: Caddr=16#00000146, Bereich: Gepufferter DB-Bereich, Adr: 11357

Kommendes Ereignis
11.05.2017 17:11:08.305



Und hier der Quellcode des Bausteins, ich habe die Stelle rot markiert an die er mir springt wenn ich auf den Butten im Editor öffnen klicke.

Code:

FUNCTION_BLOCK "FB_Auftragspruefung_NEU"
{ S7_Optimized_Access := 'TRUE' }
VERSION : 0.1
  VAR_INPUT
      IN_Einlagern : Bool;  // Auftrag: Einlagern eines Stapels
      IN_Auslagern : Bool;  // Auftrag: Auslagern eines Stapels
      IN_Umlagern : Bool;  // Auftrag: Umlagern eines Stapels
      IN_Kantholz : Bool;  // Auftrag ist eine Kantholzbox
      IN_Reset : Bool;  // Zurücksetzen der Auftrag OK/nicht OK Merker
      IN_Quelle : String[4];  // Bezeichnung der Quelle
      IN_Ziel : String[4];  // Bezeichnung des Lagerorts
      IN_Aufnahmefoerd : String[4];  // Kennung des Aufnahmeförderers
      IN_Abgabefoerd : String[4];  // Kennung des Abgabeförderers
      IN_Kantholzfoerd : String[4];  // Kennung des Kantholzförderers
      IN_Reihe_Ein : Int;  // Nummer der Lagerreihe (Einlagern)
      IN_Tiefe_Ein : Int;  // Nummer der Lagertiefe (Einlagern)
      IN_Ebene_Ein : Int;  // Nummer der Lagerebene (Einlagern)
      IN_Hoehe_Ein : DInt;  // Physikalische Höhe (Einlagern)
      IN_Reihe_Aus : Int;  // Nummer der Lagerreihe (Auslagern)
      IN_Tiefe_Aus : Int;  // Nummer der Lagertiefe (Auslagern)
      IN_Ebene_Aus : Int;  // Nummer der Lagerebene (Auslagern)
      IN_Hoehe_Aus : DInt;  // Physikalische Höhe (Auslagern)
      IN_TE_Hoehe : Int;  // Höhe der TE aus Fahrauftrag
      IN_uGrenzw_Hoehe : DInt;  // Unterer Grenzwert für die Abweichung der Höhe des Fahrauftrags zur gespeicherten Höhe im Positions-DB
      IN_oGrenzw_Hoehe : DInt;  // Oberer Grenzwert für die Abweichung der Höhe des Fahrauftrags zur gespeicherten Höhe im Positions-DB
  END_VAR

  VAR_OUTPUT
      OUT_Auftrag_OK : Bool;  // Auftrag plausibel
      OUT_Auftrag_nOK : Bool;  // Auftrag nicht ausführbar
      OUT_Platz_belegt : Bool;  // Einlagern / Umlagern: Ziel belegt
      OUT_Platz_frei : Bool;  // Auslagern: Platz frei
  END_VAR

  VAR
      STAT_nAusfuehrbar : Bool;  // Auftrag nicht ausführbar
      STAT_Platz_belegt : Bool;  // Einlagern / Umlagern: Ziel belegt
      STAT_Platz_frei : Bool;  // Auslagern: Platz frei
  END_VAR

  VAR_TEMP
      TMP_Hoehe_Rest_Aus : DInt;  // Resthöhe Auslagern (Höhe Positions-DB - Höhe Fahrauftrag)
      TMP_Hoehe_Rest_Ein : DInt;  // Resthöhe Einlagern (Höhe Positions-DB - Höhe Fahrauftrag)
  END_VAR


BEGIN
    (*
    Prüfung ob erhaltener Fahrauftrag plausibel
   
    Sprung zwischen Lagerabbild-DB und Positions-DB ist möglich, da sie den gleichen Aufbau haben
    Aufbau Positions-DB:    Reihe[1..9].Tiefe[1..19]
    Aufbau Lagerabbild-DB:  Reihe[1..9].Tiefe[1..19].Ebene[1..9]
    *)
    //==========================================================================================================================================================================================
    //                      Prüfen ob Koordinaten des Fahrauftrags im Lagerabbild vorhanden sind
    //==========================================================================================================================================================================================
                                                                                                                                        // Kommentar zu den Codezeilen
                                                                                                                                        // =====================================================
    IF (#IN_Reihe_Ein > 9) OR (#IN_Reihe_Aus > 9) OR                                                                                    // Abfrage ob Reihe größer 9
        (#IN_Tiefe_Ein > 19) OR (#IN_Tiefe_Aus > 19) OR                                                                                // Abfrage ob Tiefe größer 19
        (#IN_Ebene_Ein > 9) OR (#IN_Ebene_Aus > 9) THEN                                                                                // Abfrage ob Ebene größer 10
        #STAT_nAusfuehrbar := TRUE;                                                                                                    // Setzen Merker Auftrag nicht ausführbar
    END_IF;                                                                                                                            //
    //==========================================================================================================================================================================================
    //                      Auftragsprüfung wenn Koordinaten im Lagerabbild vorhanden sind
    //==========================================================================================================================================================================================
                                                                                                                                        // Kommentar zu den Codezeilen
                                                                                                                                        // =====================================================
    IF NOT #STAT_nAusfuehrbar AND #IN_Einlagern AND NOT (#IN_Ziel = #IN_Abgabefoerd OR #IN_Ziel = #IN_Kantholzfoerd) THEN              // Abfrage ob Ausführbar und Einlagern und Ziel nicht Abgabe- oder Kantholzförderer
        #TMP_Hoehe_Rest_Ein := ("DB_Positionen".Reihe[#IN_Reihe_Ein].Tiefe[#IN_Tiefe_Ein].Z - #IN_Hoehe_Ein);                          // Resthöhe Positions-DB - Fahrauftrag berechnen
        IF ("DB_Lagerabbild".Reihe[#IN_Reihe_Ein].Tiefe[#IN_Tiefe_Ein].Nicht_vorhanden) OR                                              // Abfrage ob Ziel physikalisch vorhanden
            (NOT #IN_Kantholz AND ((#IN_Reihe_Ein <= 2 AND #IN_Tiefe_Ein <= 3) OR #IN_Ziel = #IN_Kantholzfoerd OR #IN_Quelle = #IN_Kantholzfoerd)) OR                    // Abfrage ob Holzstapel auf Kantholzplatz soll
            (#IN_Kantholz AND ((#IN_Reihe_Ein <= 2 AND #IN_Tiefe_Ein > 3))) OR                                                          // Abfrage ob Kantholzbox auf Holzstapelplatz soll
            (NOT "DB_Lagerabbild".Reihe[#IN_Reihe_Ein].Tiefe[#IN_Tiefe_Ein].Ebene[#IN_Ebene_Ein - 1].Belegt AND #IN_Ebene_Ein >2) THEN  // Abfrage ob der darunter liegende Platz frei ist
            #STAT_nAusfuehrbar := TRUE;                                                                                                // Setzen Merker Auftrag nicht ausführbar
        ELSIF NOT #STAT_nAusfuehrbar AND "DB_Lagerabbild".Reihe[#IN_Reihe_Ein].Tiefe[#IN_Tiefe_Ein].Ebene[#IN_Ebene_Ein].Belegt OR      // Abfrage ob vorgegebenes Ziel belegt ist
            (#TMP_Hoehe_Rest_Ein > #IN_oGrenzw_Hoehe) OR                                                                                // Abfrage ob Physikalische Höhe außerhalb der Grenze liegt
            (#TMP_Hoehe_Rest_Ein < #IN_uGrenzw_Hoehe) THEN                                                                              // Abfrage ob Physikalische Höhe außerhalb der Grenze liegt
            #STAT_Platz_belegt := TRUE;                                                                                                // Setzen Merker Platz belegt (Einlagern)
        ELSE                                                                                                                            //
            #OUT_Auftrag_OK := TRUE;                                                                                                    // Setzen Ausgang Auftrag OK (Einlagern)
        END_IF;                                                                                                                        //
    ELSIF NOT #STAT_nAusfuehrbar AND #IN_Auslagern THEN                                                                                // Abfrage ob Ausführbar und Auslagern
        #TMP_Hoehe_Rest_Aus := ("DB_Positionen".Reihe[#IN_Reihe_Aus].Tiefe[#IN_Tiefe_Aus].Z - #IN_Hoehe_Aus - #IN_TE_Hoehe);            // Resthöhe Positions-DB - Fahrauftrag berechnen
        IF ("DB_Lagerabbild".Reihe[#IN_Reihe_Aus].Tiefe[#IN_Tiefe_Aus].Nicht_vorhanden) OR                                              // Abfrage ob Quelle physikalisch vorhanden
            (NOT #IN_Kantholz AND ((#IN_Reihe_Aus <= 2 AND #IN_Tiefe_Aus <= 3) OR #IN_Ziel = #IN_Kantholzfoerd)) OR                    // Abfrage ob Holzstapel von Kantholzplatz geholt werden soll
            (#IN_Kantholz AND ((#IN_Reihe_Aus <= 2 AND #IN_Tiefe_Aus > 3))) OR                                                          // Abfrage ob Kantholzbox von Holzstapelplatz geholt werden soll
            "DB_Lagerabbild".Reihe[#IN_Reihe_Aus].Tiefe[#IN_Tiefe_Aus].Ebene[#IN_Ebene_Aus + 1].Belegt THEN                            // Abfrage ob der darüber liegende Platz belegt ist
            #STAT_nAusfuehrbar := TRUE;                                                                                                // Setzen Merker Auftrag nicht ausführbar
        ELSIF NOT #STAT_nAusfuehrbar AND (NOT "DB_Lagerabbild".Reihe[#IN_Reihe_Aus].Tiefe[#IN_Tiefe_Aus].Ebene[#IN_Ebene_Aus].Belegt OR // Abfrage ob vorgegebenee Quelle frei ist
            (#TMP_Hoehe_Rest_Aus > #IN_oGrenzw_Hoehe) OR                                                                                // Abfrage ob Physikalische Höhe außerhalb der Grenze liegt
            (#TMP_Hoehe_Rest_Aus < #IN_uGrenzw_Hoehe)) THEN                                                                            // Abfrage ob Physikalische Höhe außerhalb der Grenze liegt
            #STAT_Platz_frei := TRUE;                                                                                                  // Setzen Merker Platz frei (Auslagern)
        ELSE                                                                                                                            //
            #OUT_Auftrag_OK := TRUE;                                                                                                    // Setzen Ausgang Auftrag OK (Auslagern)
        END_IF;                                                                                                                        //
    ELSIF NOT #STAT_nAusfuehrbar AND #IN_Umlagern THEN                                                                                  // Abfrage ob Ausführbar und Umlagern
        #TMP_Hoehe_Rest_Ein := ("DB_Positionen".Reihe[#IN_Reihe_Ein].Tiefe[#IN_Tiefe_Ein].Z - #IN_Hoehe_Ein);                          // Resthöhe Positions-DB - Fahrauftrag berechnen
        #TMP_Hoehe_Rest_Aus := ("DB_Positionen".Reihe[#IN_Reihe_Aus].Tiefe[#IN_Tiefe_Aus].Z - #IN_Hoehe_Aus - #IN_TE_Hoehe);            // Resthöhe Positions-DB - Fahrauftrag berechnen
        IF ("DB_Lagerabbild".Reihe[#IN_Reihe_Ein].Tiefe[#IN_Tiefe_Ein].Nicht_vorhanden) OR                                              // Abfrage ob Ziel physikalisch vorhanden
            ("DB_Lagerabbild".Reihe[#IN_Reihe_Aus].Tiefe[#IN_Tiefe_Aus].Nicht_vorhanden) OR                                            // Abfrage ob Quelle physikalisch vorhanden
            (NOT #IN_Kantholz AND ((#IN_Reihe_Ein <= 2 AND #IN_Tiefe_Ein <= 3) OR #IN_Ziel = #IN_Kantholzfoerd OR #IN_Quelle = #IN_Kantholzfoerd)) OR                    // Abfrage ob Holzstapel auf Kantholzplatz soll
            (#IN_Kantholz AND ((#IN_Reihe_Ein <= 2 AND #IN_Tiefe_Ein > 3))) OR                                                          // Abfrage ob Kantholzbox auf Holzstapelplatz soll
            (NOT #IN_Kantholz AND ((#IN_Reihe_Aus <= 2 AND #IN_Tiefe_Aus <= 3) OR #IN_Ziel = #IN_Kantholzfoerd)) OR                    // Abfrage ob Holzstapel von Kantholzplatz geholt werden soll
            (#IN_Kantholz AND ((#IN_Reihe_Aus <= 2 AND #IN_Tiefe_Aus > 3))) OR                                                          // Abfrage ob Kantholzbox von Holzstapelplatz geholt werden soll
            (NOT "DB_Lagerabbild".Reihe[#IN_Reihe_Ein].Tiefe[#IN_Tiefe_Ein].Ebene[#IN_Ebene_Ein - 1].Belegt AND #IN_Ebene_Ein >2) OR    // Abfrage ob der darunter liegende Platz frei ist
            "DB_Lagerabbild".Reihe[#IN_Reihe_Aus].Tiefe[#IN_Tiefe_Aus].Ebene[#IN_Ebene_Aus + 1].Belegt THEN                            // Abfrage ob der darüber liegende Platz belegt ist
            #STAT_nAusfuehrbar := TRUE;                                                                                                // Setzen Merker Auftrag nicht ausführbar
        ELSIF NOT #STAT_nAusfuehrbar AND ("DB_Lagerabbild".Reihe[#IN_Reihe_Ein].Tiefe[#IN_Tiefe_Ein].Ebene[#IN_Ebene_Ein].Belegt OR    // Abfrage ob vorgegebenes Ziel belegt ist
            (#TMP_Hoehe_Rest_Ein > #IN_oGrenzw_Hoehe) OR                                                                                // Abfrage ob Physikalische Höhe außerhalb der Grenze liegt
            (#TMP_Hoehe_Rest_Ein < #IN_uGrenzw_Hoehe)) THEN                                                                            // Abfrage ob Physikalische Höhe außerhalb der Grenze liegt
            #STAT_Platz_belegt := TRUE;                                                                                                // Setzen Merker Platz belegt (Umlagern)
        ELSIF NOT #STAT_nAusfuehrbar AND (NOT "DB_Lagerabbild".Reihe[#IN_Reihe_Aus].Tiefe[#IN_Tiefe_Aus].Ebene[#IN_Ebene_Aus].Belegt OR // Abfrage ob vorgegebenee Quelle frei ist
            (#TMP_Hoehe_Rest_Aus > #IN_oGrenzw_Hoehe) OR                                                                                // Abfrage ob Physikalische Höhe außerhalb der Grenze liegt
            (#TMP_Hoehe_Rest_Aus < #IN_uGrenzw_Hoehe)) THEN                                                                            // Abfrage ob Physikalische Höhe außerhalb der Grenze liegt
            #STAT_Platz_frei := TRUE;                                                                                                  // Setzen Merker Platz frei (Umlagern)
        ELSE                                                                                                                            //
            #OUT_Auftrag_OK := TRUE;                                                                                                    // Setzen Ausgang Auftrag OK (Umlagern)
        END_IF;                                                                                                                        //
    ELSIF NOT #STAT_nAusfuehrbar AND #IN_Einlagern AND (#IN_Ziel = #IN_Abgabefoerd OR #IN_Ziel = #IN_Kantholzfoerd) THEN                //                                                                                                                //
        #OUT_Auftrag_OK := True;                                                                                                        //
    END_IF;                                                                                                                            //
    //==========================================================================================================================================================================================
    //                          Setzen der Ausgänge
    //==========================================================================================================================================================================================
    #OUT_Auftrag_nOK := #STAT_nAusfuehrbar;                                                                                            // Setzen Ausgang Auftrag nicht ausführbar
    #OUT_Platz_belegt := #STAT_Platz_belegt;                                                                                            // Setzen Ausgang Platz belegt
    #OUT_Platz_frei := #STAT_Platz_frei;                                                                                                // Setzen Ausgang Platz frei
    //==========================================================================================================================================================================================
    //                          Rücksetzen der Merker und Ausgänge
    //==========================================================================================================================================================================================
    IF #IN_Reset THEN                                                                                                                  // Abfrage ob Reset
        #STAT_nAusfuehrbar := FALSE;                                                                                                    // Rücksetzen Merker nicht Ausführbar
        #STAT_Platz_frei := FALSE;                                                                                                      // Rücksetzen Merker Platz frei
        #STAT_Platz_belegt := FALSE;                                                                                                    // Rücksetzen Merker Platz belegt
        #OUT_Auftrag_OK := FALSE;                                                                                                      // Rücksetzen Ausgang Auftrag OK
    END_IF;                                                                                                                            // 
   
   
END_FUNCTION_BLOCK

#IN_Kantholz ist ein Bool und wird von außen auch mit einem Bool aus einem Global-DB beschaltet. Ich weiß, dass der Code nicht elegant ist, aber das waren meine ersten SCL Gehversuche also habt bitte etwas Rücksicht ;)

Achja verwendet wird TIA Portal V13 SP1, die CPU ist eine 1515F-2 PN. Ich hoffe das sind alle Infos die ihr braucht.

Gruß ThomasM

Viewing all articles
Browse latest Browse all 47324


<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>