Step 7 interner Fehler FB63 TSend in SCL

RMLIF

Level-1
Beiträge
29
Reaktionspunkte
0
Zuviel Werbung?
-> Hier kostenlos registrieren
Hallo Zussammen
hab mal eine frage bezüglich des aufrufes vom fb63 Tsend
Ich bekomme immer als Fehlermeldung des Bausteines 887F zurück
wenn ich es richtig Verstanden habe hat der Bausteine einen internen Fehler am 8 Parameter nur welcher Parameter ist das und was ist der Fehler
im Anhang mal der SCL Code vielleicht kann mir da ja einer weiter helfen
Danke schon mal Grüße Rudi


FUNCTION_BLOCK FB201

// Bausteinparameter
VAR_INPUT
// Eingangsparameter


IN_Scanner_Ergebniss: STRING [64];
IN_Scanner_Ein: BOOL;
IN_Scanner_Ergeb_Akt:BOOL;
IN_iTAC_Senden:BOOL;
IN_Stoerung_Qitt:BOOL;
Stationsnummer:INT;
TCP_CONNECTED:BOOL;
TCP_Verbindung:WORD;
END_VAR

VAR_IN_OUT
// Durchgangsparameter

IO_Text_Fehlermeldung:STRING[64];
IO_iTAC_IO:BOOL;
IO_iTAC_NIO:BOOL;
IO_iTac_Fehlermeldung:BOOL;

END_VAR

VAR_OUTPUT
// Ausgangsparameter
O_Busy:BOOL;
O_Done:BOOL;
END_VAR


VAR_TEMP
// temporäre Variablen
test:ANY;
END_VAR
VAR
// statische Variablen
VAR_Text_Fehlermeldung:STRING[64];
iTAC_DMC_String:STRING[64];
Rueckmeldung_iTAC:STRING[64];
iTAC_DMC_String_Teil1:String[64];
iTAC_DMC_String_Teil2:String[64];
iTAC_IO:BOOL;
iTAC_NIO:BOOL;
iTAC_Fehlermeldung:BOOL;
Stationsnummer_Konst:ARRAY[1..4]OF STRING[64];
Stationsnummer_STRING:STRING[64];
IO_Ergebniss:INT;
NIO_Ergebniss:INT;
Send:FB63;
Send_Start:BOOL;
Send_Done:BOOL;
Send_Busy:BOOL;
Send_Error:BOOL;
Send_Status:WORD;
Recive:FB64;
Recive_Start:BOOL;
Recive_NDR:BOOL;
Recive_Busy:BOOL;
Recive_Error:BOOL;
Recive_Status:WORD;
Recive_LEN:INT;
Schrittkette:INT;

END_VAR
//STRING INIT

Rueckmeldung_iTAC:='1234567890123456789012345678901234567890123456789012345678901234';
iTAC_DMC_String:= ' ';

// Aufruft Tsend Bausteine
Send(REQ := Send_Start // IN: BOOL
,ID :=TCP_Verbindung // IN: WORD
,LEN := 64 // IN: INT
,DATA :=iTAC_DMC_String );// INOUT: ANY

Send_Done:= Send.DONE; // OUT: BOOL
Send_Busy:= Send.BUSY; // OUT: BOOL
Send_Error:= Send.ERROR; // OUT: BOOL
Send_Status:= Send.STATUS; // OUT: WORD

// Aufruft TResive Bausteine

Recive(EN_R :=Recive_Start // IN: BOOL
,ID :=TCP_Verbindung // IN: WORD
,LEN :=0 // IN: INT
,DATA :=Rueckmeldung_iTAC // INOUT: ANY
);
Recive_NDR := Recive.NDR; // OUT: BOOL
Recive_Busy := Recive.BUSY; // OUT: BOOL
Recive_Error := Recive.ERROR; // OUT: BOOL
Recive_Status:= Recive.STATUS; // OUT: WORD
Recive_LEN:= Recive.RCVD_LEN; // OUT: INT
//STRING INIT


// Vorgaben Rückmeldungen
Stationsnummer_Konst[1]:='01;';
Stationsnummer_Konst[2]:='02;';
Stationsnummer_Konst[3]:='03;';
Stationsnummer_Konst[4]:='04;';

// Stationnummer auswerten
Stationsnummer_STRING:=Stationsnummer_Konst[Stationsnummer];

IF NOT IN_Scanner_Ein AND IN_Scanner_Ergeb_Akt THEN
// iTAC STRING zusammensetzten

iTAC_DMC_String_Teil1:=CONCAT(IN1 := '' // IN: STRING
,IN2 :=Stationsnummer_Konst[Stationsnummer] // IN: STRING
); // STRING

iTAC_DMC_String_Teil2:=CONCAT(IN1 := iTAC_DMC_String_Teil1 // IN: STRING
,IN2 :=IN_Scanner_Ergebniss // IN: STRING
); // STRING

iTAC_DMC_String:=CONCAT(IN1 := iTAC_DMC_String_Teil2 // IN: STRING
,IN2 :='$r$l'

); // STRING
END_IF;






IF IN_iTAC_Senden THEN
Schrittkette:=1;

END_IF;


CASE Schrittkette OF
1 : IF TCP_CONNECTED THEN
Send_Start:=true;
O_Busy:=true;
O_Done:=false;

Schrittkette:=3;
END_IF;;

3 : IF Send_Busy THEN
Send_Start:=false;
Schrittkette:=5;
END_IF;;


5 : IF Send_Done THEN
Recive_Start:= true;
Schrittkette:=10;
END_IF;;

10 : IF Recive_Busy THEN
Recive_Start:= false;
Schrittkette:=15;
END_IF;;

15 : IF Recive_NDR THEN

IO_Ergebniss:= FIND(IN1 := Rueckmeldung_iTAC // IN: STRING
,IN2 := '0;OK;' // IN: STRING
); // INT
NIO_Ergebniss:= FIND(IN1 := Rueckmeldung_iTAC // IN: STRING
,IN2 := '2;' // IN: STRING
); // INT

Schrittkette:=20;
END_IF;;

20 : IF IO_Ergebniss = 8 THEN
iTAC_IO:=true;
iTAC_NIO:=False; // Anweisungsteil_IF
Schrittkette:=25;
END_IF;

IF NIO_Ergebniss = 8 THEN
iTAC_IO:=false;
iTAC_NIO:=true; // Anweisungsteil_IF
iTAC_Fehlermeldung:=true;
Schrittkette:=25;

END_IF;;
25 : IF IO_Ergebniss = 8 THEN
iTAC_IO:=true;
iTAC_NIO:=False; // Anweisungsteil_IF
Schrittkette:=0;
END_IF;;

END_CASE;

IO_iTAC_IO:=iTAC_IO;
IO_iTAC_NIO:=iTAC_NIO;
IO_iTac_Fehlermeldung:=iTAC_Fehlermeldung;

IF iTAC_NIO THEN

VAR_Text_Fehlermeldung:= DELETE(IN := Rueckmeldung_iTAC // IN: STRING
,L :=NIO_Ergebniss // IN: INT
,P :=1 // IN: INT
); // STRING
ELSE
VAR_Text_Fehlermeldung:= ' ';

END_IF;

// ALTE PROGRAMMTEILE
// Abfrage IO_NIO iTAC

// Abfrage iTAC Ergebniss String
// IO_Ergebniss:= FIND(IN1 := Rueckmeldung_iTAC // IN: STRING
// ,IN2 := '0;OK;' // IN: STRING
// ); // INT
// NIO_Ergebniss:= FIND(IN1 := Rueckmeldung_iTAC // IN: STRING
// ,IN2 := '2;' // IN: STRING
// ); // INT

END_FUNCTION_BLOCK
 
Hallo,
ich vermisse irgendwie den Connect (FB65).
Rufst du den irgendwo anders auf - oder ggf. bislang gar nicht ?
Hat das Ganze schon mal funktioniert ?

Gruß
Larry
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Parameter 8 ist der Parameter DATA. Die Zählweise der Parameter-Nummern geht nach der Reihenfolge wie die Parameter später im Instanz-DB abgelegt werden. Erst In, dann Out, dann In_Out durchzählen.
Ich sehe in dem Aufruf erstmal keinen Grund dass es dort etwas zu meckern geben sollte.

Wobei ich selber nie direkt einen S7-String verschicke, da du auch immer die zwei Header-Bytes für die Längenangaben mitverschickst. Sollte dein Partner eine S7 sein die ebenfalls S7-Strings versendet/empfängt ist das folgende hinfällig.
Wenn bei dir dein String wirklich aktuell 64 Zeichen lang wäre, würden die letzten beiden Zeichen nicht mitveschickt. Dafür würde der Empfänger aber in den ersten beiden Zeichen zweimal 64 stehen haben (weil Aktual- und Maximallänge in diesem Fall gleich, Zeichen '@' würde er dann zu sehen bekommen).
Um das zu beheben könntest du den String auf ein Byte- oder Char-Array zum Senden umkopieren. Gleiches Problem hast du auch beim Empfang eines Strings.

Aber zu deinem eigentlichen Problem mit dem Fehlercode 887f, würde ich einfach mal probieren deinen FB und zugehörigen Instanz-DB neu zu laden, ggf. SPS einmal auf Stop setzen. Vielleicht war einmal der Instanz-DB nicht aktuell.
 
Hallo Zusammen

@larry laffer
ja connect und disconect rufe ich in einem anderen Bausteine auf und übergeben die Rückmeldungen über die Schnittstelle
ich hab die funktion davor in einem anderen Bausteine bereits beim laufen gehabt allerdings hab ich es da mit einem array of byte laufen gehabt

@ thomas
das mit dem neu übertragen hab ich schon versucht
im Moment hab ich den Gedanken das es am string liegt das ich den in der ganzen länge
initialisieren muss
 
Da fällt mir mit dem String und SCL noch was ein, könnte evlt. wirklich daran liegen.

Denn der SCL-Compiler setzt wenn man einen Parameter Any hat, den Datentyp in diesem Any-Parameter wirklich auf String (16#13) . Wenn man den Aufruf hingegen in AWL macht, dann wird als Any-Pointer quasi ein Array of Byte generiert. Vielleicht kennt der Baustein der in dem Tsend-FB aufgerufen wird diesen String Any-Datentyp nicht oder kann damit nicht umgehen, weil in diesem als Längenangabe nämlich 1 steht, was mit deinem Parameter LEN=64 dann nicht zusammenpasst.
Intern wird im Tsend ein SFC131 aufgerufen, der ist aber nirgends dokumentiert.

Du kannst versuchen eine At-Sicht über den String zu legen. Dann hast du am Anfang zwei einzelne Bytes und dann ein Array of Byte. Das Array übergibst du dann dem Tsend-FB.

Du solltest aber bedenken, dass wenn du einen String überschreibst, die Zeichen im zugehörigen Speicher erhalten bleiben.
Beispiel:
str : STRING[3];

Intern werden für den String str 5 Bytes verwendet die folgendermaßen belegt sind:

str := "abc";
Byte0 = 3, Byte1 = 3, Byte2 = 'a', Byte3 = 'b', Byte4 = 'c'

Wenn du dann str überschreibst mit:

str := "x";

stehen in den Bytes:
Byte0 = 3, Byte1 = 1, Byte2 = 'x', Byte3 = 'b', Byte4 = 'c'

Wenn du dann die 3 Bytes an deinen Partner schicken würdest, sähe dieser "xbc". Wahrscheinlich ist das nicht das was gewollt ist.
 
Zuviel Werbung?
-> Hier kostenlos registrieren
ich fülle den string am ende mit Leerzeichen auf bis er bei 64 zeichnen ist damit genau diese Effekt nicht auftritt
wie muss ich das mit der at Ansicht machen hab ich heute zum ersten mal gelesen ?
 
Eine At-Sicht sieht so aus:
Code:
VAR
    str : STRING[64];    // der eigentliche String
    at_str AT str : STRUCT // AT-Sicht auf die Variable "str"
        max_length : BYTE;  // Maximale Länge des Strings
        act_length : BYTE;  // Aktuelle Länge des Strings
        chars : ARRAY [1..64] OF CHAR; // Die einzelnen Zeichen
    END_STRUCT;
END_VAR

Dem Tsend übergibst du dann als Parameter: at_str.chars

Das liegt garantiert daran, hab gerade nochmal getestet was der SCL-Übersetzer für einen Any-Pointer generiert.

Wenn man eine Funktion mit dem Parameter ANY in SCL aufruft macht dieser wenn die Variable vom Typ String ist einen Any-Pointer mit:
Datentyp = 16#13 -> Typ String
Wiederholfaktor = 1 -> Ist immer 1, unabhängig von der Länge des Strings. Die aufgerufene Funktion müsste dann den String-Kopf auswerten

Und das kann der TSEND bzw. der unterlagerte SFC wohl nicht. Leider ist dieses Verhalten nirgends dokumentiert.
 
ok werd ich morgen gleich mal ausprobieren
danke thomas ich meld mich noch mal wenn ich ein Ergebnis habe
 
Oh, das wußte ich auch noch nicht. Aber da ein S7-String ohnehin etwas anders aufgebaut ist als ein normaler String habe ich schon immer Arrays of Byte empfangen und dies dann zu einem String gewandelt oder umgekehrt. Schade, dass der SCL-Compiler einem dazu nichts vernünftiges sagt.
 
Zurück
Oben