Zuviel Werbung? - > Hier kostenlos beim SPS-Forum registrieren

Seite 1 von 2 12 LetzteLetzte
Ergebnis 1 bis 10 von 14

Thema: S7-1500 SCL Any Pointer auf UDT zuweisen

  1. #1
    Registriert seit
    30.06.2009
    Beiträge
    11
    Danke
    0
    Erhielt 2 Danke für 2 Beiträge

    Standard


    Zuviel Werbung?
    -> Hier kostenlos registrieren
    Hallo zusammen,

    folgendes Problem:

    Aus einem S7-300 Projekt muss ich Bausteine für die nutzung in einer S7-1500 umwandeln.
    In den alten Bausteinen wird ein UDT als INPUT Parameter an eine Funktion übergeben. Innerhalb der Funktion wird ein Any Pointer auf diese Struktur erzeugt, und der Pointer in einem DB gesichert.
    Ein anderer Baustein lädt diesen Pointer und beschreibt den Speicherbereich mit gültigen Daten. Das ganze funktioniert auch schon so, wie ich mir das vorstelle.

    Allerdings nicht mehr, wenn ich versuche den SCL Code für eine S7-1500 zu kompilieren.

    Als beispiel hier mal folgender Baustein auf der S7-300:

    Code:
    FUNCTION FC100 : VOID
    
    VAR_INPUT
        SESSION : tHSC_Session;
    END_VAR
    
    VAR_TEMP
        pSession : ANY;
    END_VAR
    
        pSession := SESSION;
        
    END_FUNCTION

    und hier der leicht abgewandelte Code für die S7-1500:

    Code:
    FUNCTION "Test" : Void
    { S7_Optimized_Access := 'FALSE' }
    VERSION : 0.1
       VAR_INPUT 
          SESSION : "tHSC_Session";
       END_VAR
    
       VAR_TEMP 
          pSession : Any;
       END_VAR
    
    
    BEGIN
        #pSession := #SESSION;
    END_FUNCTION
    Als Fehlermeldung erhalte ich hier aber:
    "Ungültige Zusweisung"
    Wo liegt bei mir jetzt der Denkfehler, bzw. wie kann ich in SCL auf einer S7-1500 einen Any Pointer auf eine Struktur erzeugen, welche als Input Parameter übergeben wird?


    Vielen Dank schonmal im Vorraus
    Zitieren Zitieren S7-1500 SCL Any Pointer auf UDT zuweisen  

  2. #2
    Registriert seit
    19.06.2015
    Beiträge
    459
    Danke
    26
    Erhielt 40 Danke für 35 Beiträge

    Standard

    Für was braucht man eigentlich einen Any-Pointer auf einen UDT.
    Ich kann doch direkt drauf zugreifen.Also ich verstehe das nicht.

  3. #3
    kamikaaze ist offline Neuer Benutzer
    Themenstarter
    Registriert seit
    30.06.2009
    Beiträge
    11
    Danke
    0
    Erhielt 2 Danke für 2 Beiträge

    Standard

    Ok. Ich versuche mal etwas mehr zu erklären.

    Im Anhang ein Beispiel, wie die Funktionen im Programm aufgerufen werden.

    Am Ersten Baustein (FC1101) wird der UDT übergeben. Dieser wird vom Baustein in einem temporären DB gesichert (hier nicht zu sehen). Anschließend wird mit beliebig vielen funktionen diese "Session" erweitert und mit dem letzten Baustein (FC1109) wieder zurück auf den UDT kopiert.
    Ich brauche den Pointer also, damit ich nicht am letzten Baustein wieder die Session angeben muss (Weniger Aufwand / Fehler / Arbeit bei Inbetriebnahme der Funktionen bzw. Änderung )

    Falls es dafür aber eine noch sauberere / einfachere Lösung gibt, bin ich für vorschläge offen.

    HSC.png

  4. #4
    Registriert seit
    22.06.2009
    Ort
    Sassnitz
    Beiträge
    11.207
    Danke
    927
    Erhielt 3.293 Danke für 2.662 Beiträge

    Standard

    Zitat Zitat von kamikaaze Beitrag anzeigen
    Ich brauche den Pointer also, damit ich nicht am letzten Baustein wieder die Session angeben muss (Weniger Aufwand / Fehler / Arbeit bei Inbetriebnahme der Funktionen bzw. Änderung )
    Wo gibst Du denn am letzten Baustein "den Pointer" bzw. die "Session" an? Woher weiß der FC1109, wohin er den temporären UDT zurück-kopieren muß?
    Deine gekürzte Bausteinerklärung sieht mir irgendwie noch relativ verworren aus. Vielleicht läßt Du uns mehr Details sehen.

    Um den UDT von Input in eine Arbeitskopie zu kopieren braucht man keinen ANY erzeugen, da kümmert sich SCL bei Bedarf selber drum:
    Code:
      "MyTempDB".Arbeitskopie := #SESSION;
    Wie groß ist der UDT? Der wird ja mindestens 4 mal kopiert. Man könnte argumentieren, daß er an IN_OUT passender wäre, zumal er ja tatsächlich auch beschrieben wird.

    Harald
    Es ist immer wieder überraschend, wie etwas plötzlich funktioniert, sobald man alles richtig macht.

    FAQ: Linkliste SIMATIC-Kommunikation über Ethernet

  5. #5
    kamikaaze ist offline Neuer Benutzer
    Themenstarter
    Registriert seit
    30.06.2009
    Beiträge
    11
    Danke
    0
    Erhielt 2 Danke für 2 Beiträge

    Standard

    Wohin der temporäre UDT kopiert werden muss, weiß ich dann ja über den ANY Pointer, den ich mir im ersten Baustein erzeugt und gesichert habe
    Das ich die Daten mit dem Obigen Befehl umkopieren kann ist mir auch klar, auch wenn ich dazu den SFC20 - BLKMOV nutze, da der etwas schneller arbeitet.

    Im Anhang mal die Struktur der Temporären Daten.

    Im ersten Baustein werden wird die Session zwischengespeichert (Offset +0.0), sowie der Pointer auf den ursprünglichen UDT (Offset +2312.0).
    Der letzte Baustein (FC1109) lädt sich dann wieder den ANY Pointer aus den Temporären Daten, und kopiert mittels SFC20 - BLKMOV die Daten zurück auf den originalen UDT.

    Das ganze funktioniert ja auch schon wunderbar auf einer 300-er CPU. Allerdings lässt sich der Any Pointer auf einer 1500-er nicht erzeugen.

    temp.png

  6. #6
    Registriert seit
    22.06.2009
    Ort
    Sassnitz
    Beiträge
    11.207
    Danke
    927
    Erhielt 3.293 Danke für 2.662 Beiträge

    Standard

    Gibt es den SFC20 überhaupt auf der S7-1500? Funktioniert der ggf. auch mit '"optimierten" DB? Wieso nimmst Du an, daß ein von Dir erzwungener BLKMOV schneller arbeitet als ein vom SCL-Compiler automatisch erzeugtes Kopieren?


    (A) Du könntest Deine Bausteinaufrufe umstellen und in einen "Session-Bearbeiten"-FC/FB einbetten (statt dem FC1101) und aus diesem Baustein auch das zurückkopieren ausführen. Dann braucht man sich die Adresse des übergebenen UDT #SESSION nicht merken.

    Inhalt des "Session-Bearbeiten"-FC/FB:
    - kopieren von #SESSION in globale Arbeitskopie
    - Aufruf FC1102
    - Aufruf FC1107
    - zurückkopieren von globaler Arbeitskopie zu #SESSION


    (B) Deine "Sessions" kommen immer aus einem Array? Du könntest alternativ statt der Adresse den Array-Index übergeben.

    Harald
    Es ist immer wieder überraschend, wie etwas plötzlich funktioniert, sobald man alles richtig macht.

    FAQ: Linkliste SIMATIC-Kommunikation über Ethernet

  7. #7
    Registriert seit
    19.06.2015
    Beiträge
    459
    Danke
    26
    Erhielt 40 Danke für 35 Beiträge

    Standard

    Genau.Wieso kein Array aus Datenstrukturen?

  8. #8
    kamikaaze ist offline Neuer Benutzer
    Themenstarter
    Registriert seit
    30.06.2009
    Beiträge
    11
    Danke
    0
    Erhielt 2 Danke für 2 Beiträge

    Standard

    Danke für die Vorschläge. Nochmal zur ursprünglichen Frage, die vielleicht nicht ganz gut rüber kam:
    Ich nehme mal an, dass die urpsrüngliche Idee also auf einer 1500-er nicht mehr funktioniert, warum auch immer?!? Bzw. warum erlaubt er mir das erstellen des ANY Pointer nicht?

    Die ganze Sache wird, vermutlich nicht auf diesen "optimierten DBS" funktionieren, aber damit habe ich mich noch nicht genug mit beschäftigt... Sollte ich vielleicht mal nachholen


    Die Idee mit den Arrays und angabe eines index hatte ich auch ganz am Anfang habe ich aber wieder verworfen aus mehreren Gründen.
    1. Die Anzahl der Einträge des Arrays ist nicht immer gleich, somit muss ich das Array als Any Pointer übergeben -> Keine / Beschränkte Typsicherheit. (OK Kann man argumentieren, dass der Programmierer wissen sollte was er tut )
    2. Es kann mehrere Arrays mit Variabler Anzahl an Einträgen geben. Eins im DB1 eins im DB2 etc.
    3. Ich muss überprüfen, ob der Index außerhalb des Array liegt. Dazu brauche ich wieder einen Any Pointer auf den UDT, um die Länge zu bestimmen. Zumindest bei einer 300-er.

    Zu den Kopierzeiten:
    Die habe ich gemessen, und wenn ich alles richtig gemacht habe, dann war der unterschiedlich deutlich spürbar in der Zykluszeit ~5-10 mal schneller. Beim kopieren, ohne SCL wird entweder eine Schleife erstellt, bzw. ein L;T Befehl nach dem anderen. SFC20 ist da deutlich schneller unterwegs. auch wenn man in die CPU Manual schaut, und die Zeiten grob hochrechnet. Ob dies noch bei 1500-er gilt, habe ich nicht überprüft!
    Ausserdem kann ich mit der aktuellen funktionalität über den ANY Pointer sowieso nur mit SFC20 arbeiten, da SCL dummerweise kein dereferenzieren von Pointern unterstützt

    Zu Vorschlag A:
    Bei deinem Vorschlag müsste ich den "Session-Bearbeiten"-FC mehrfach aufrufen? Das möchte ich ja nicht, da ich ihn dann ja auch mehrfach mit dem UDT beschalten muss. Das möchte ich nur an einer stelle machen, um fehler zu vermeiden. Ansonsten könnte ich es ja auch an den letzten Baustein schreiben.


    Sry, falls ich zu hohe Ansprüche haben sollte

  9. #9
    Registriert seit
    19.06.2015
    Beiträge
    459
    Danke
    26
    Erhielt 40 Danke für 35 Beiträge

    Standard

    Wenn die datenstruktur bleibt, kann man die Arraygröße doch an der Schnittstelle mitgeben?Kraatz?
    Die Größe der Datenstruktur steht ja vorher fest.Die wird ja nicht zur Laufzeit erzeugt.
    Das mit der Schnelligkeit kann stimmen.Wobei der SFC20 ja auch in SCL benutzt werden kann.

    Aber vielleicht sind deine Ansprüche wirklich zu hoch für mich!

  10. #10
    kamikaaze ist offline Neuer Benutzer
    Themenstarter
    Registriert seit
    30.06.2009
    Beiträge
    11
    Danke
    0
    Erhielt 2 Danke für 2 Beiträge

    Standard


    Zuviel Werbung?
    -> Hier kostenlos registrieren
    Ja, man kann die größe an der Schnittstelle mitgeben, aber dann komme ich auch nur vom Regen in die Traufe:
    - Der Programmierer (Ich ), kann wieder falsche werte angeben
    - Ich Programmiere nicht mehr zu 100% symolisch. Sprich wenn ich den UDT der Session ändere, also die größe, dann MUSS ich daran denken, die neue größe an allen stellen anzugeben, und kann nicht einfach die Bausteinkonsistenz prüfen, und der Rest im Programm passt sich einfach automatisch an. Das geht bis jetzt nämlich wunderbar

    Ok, man kann dafür auch einen SIZEOF Baustein programmieren, aber das möchte ich wieder nicht, und hilft ja auch nicht gegen mein eigentliches Problem.

Ähnliche Themen

  1. Antworten: 4
    Letzter Beitrag: 20.04.2015, 15:30
  2. Antworten: 5
    Letzter Beitrag: 13.03.2015, 12:00
  3. Pointer auf udt laden...
    Von Jochen Kühner im Forum Simatic
    Antworten: 4
    Letzter Beitrag: 24.12.2013, 15:12
  4. SCL: Pointer auf Struct in DB
    Von DunderHEAD im Forum Simatic
    Antworten: 10
    Letzter Beitrag: 13.08.2010, 10:05
  5. ANY-Pointer auf UDT mit Bestimmter Länge
    Von RONIN im Forum Simatic
    Antworten: 15
    Letzter Beitrag: 07.08.2009, 07:16

Lesezeichen

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •