CM1241 Empfangsprobleme mit Endzeichen

HarryHirn

Level-1
Beiträge
15
Reaktionspunkte
2
Zuviel Werbung?
-> Hier kostenlos registrieren
Hi,

ich krieg momentan einen Fehler nicht beseitigt und dachte mir ich poste mal hier, vielleicht hat jemand schon ein ähnliches Problem gehabt:

Mein Setup:
S7-1200 (FW 3.0.2) mit CM1241 RS422/485 (FW 1.1.0) verbunden mit Nanotec SMCI174-S-2.


Ich schreibe ein Befehl auf den Bus und die Nanotec Steuerung antwortet auch darauf.


Nun passiert aber folgendes:
Beim ersten Auslesen mit RCV_PTP bekomme ich keine Daten in mein Char Array.
Im zweiten Aufruf bekomme ich 4 Char zu viel, danach sind die Nachrichten von der Länge richtig, aber immer um 4 Char verschoben.


Die Konfiguration des CM1241 hat als Nachrichtenende 0x0D, also $R.


Empfangen sollte ich und ist auch physikalisch auf dem Bus:
0x 30 30 31 24 31 36 31 0D

Beim ersten Auslesen steht im Array:
0x 30 30 31 24 31 36 31 0D 30 30 31 24


In meinem Array liegt immer:
0x 31 36 31 0D 30 30 31 24


Ich habe mittlerweile versucht den Buffer mit RCV_RST zu löschen, aber dann fängt er mit dem Problem nur wieder von vorne an.

Ich habe das Endzeichen auf irgendeinen Wert in der Mitte der Nachricht gelegt, danach kamen ab dem neuen Endzeichen 4 Byte zuviel.

Das einzige, was funktioniert hat, ist das Abschalten der Endzeichenerkennung und das Erkennen des Nachritenendes durch Timeout.
Ich würde aber lieber aufs Endzeichen gehen aus Timing Gründen.

Hat jemand noch ne gute Idee oder muss ich einfach auf das Timeout gehen?

Danke
 
Hi!

Sind die Telegramme immer gleich lang? Wenn ja, kannst auch eine bestimmte Telegrammlänge (z.B. 9 Byte) als End-Bedingung angeben.
Das hab ich an einem kleinem BUS-System (mit dem CB1241) so am laufen und es funktioniert.
Im Vergleich zum Timeout hast du auch eine schnelle Reaktion.


Gruß,

Ottmar
 
Hi!

Hm, okay...

Ist der BUS richtig terminiert? Also ca. 150 Ohm am ersten und letzten Teilnehmer?
Beim CB1241 kann man Brücken auf RB und RA machen, damit ist dann der Abschlusswiderstand für die CPU erledigt.
Wie das beim CM1241 ist weiß ich leider nicht, hier musst du ggf. nachsehen.

Kann es sein, dass dein Empfangspuffer teilweise von deinem eigenen Programm überschrieben wird?
Gibt es noch andere Teilnehmer im BUS, oder sind die beiden Geräte die einzigen?
Du sagst du hast die Zeichen "physikalisch" auf dem BUS - hast du den Diagnoseadapter mal weggenommen und dann getestet?


Gruß,

Ottmar
 
Also ich hab in keiner Verdrahtungsanleitung was von Widerständen gelesen.
Ist ja eigentlich auch nur Punkt zu Punkt.
Aber ich schlag das noch mal nach.
Wenn ich aber die richtigen Zeichen im Puffer habe, dann kann das ja nicht so verkehrt sein, richtig?

Ich habe ein Scope dran, mit dem ich die Leitungen angezapft habe...
Mein Programm ist auch minimal und auf den Puffer greift nur das RCV_PTP zu.

Ich hab das Scope erst drangehängt als ich so komische Probleme hatte, aber abnehmen kann man ja mal :)
 
Moin Moin,

ich habe ein Array of Char angegeben, weil in der Hilfe ja auch explizit steht dass man kein String benutzen soll.
Eben wegen der String Mismatch Geschichte...
Und dann sehe ich ja jedes Byte, was da reingeschrieben wird.

Ich weiß allerdings nicht wirklich wie man da die Absolutadresse angeben kann.

Achja, ich arbeite in SCL...
 
Hi
Absolut Adrsse steht in dem Link von meinem letzten Beitrag
Global-DB erstellen mit Empfangspuffer zb Empfang der erhält dann einen Offset zb 0.0
danach %DBxx.DBX2.0 BYTE xx
gruss chris
 
Zuviel Werbung?
-> Hier kostenlos registrieren
So, ich habe es mit einem sehr engagierten Mitarbeiter vom Siemens Support lösen können.

Meine Routinen waren richtig, allerdings die Art und Weise wie ich die Konfiguration interpretiert habe waren nicht mit der Vorstellung von Siemens konform.

Bei der Konfiguration des CM in TIA11 kann man "Erkenne Nachrichtenende mit einer Zeichenkette" anhaken.
Dann kann man 5 Zeichen definieren, welche er als Nachrichtenende erkennt.
Ich habe nur ein Zeichen und habe es in Feld 1 geschrieben.
TIA dachte nun aber da kommen noch 4 weitere Zeichen (obwohl ich diese 4 Zeichen nicht durch ein Häkchen im Feld aktiviert habe), wodurch er noch 4 Byte gewartet hat.

Man muss diese Felder also von hinten befüllen.
Will man, so wie ich, nur auf ein Endzeichen warten, dann muss das in das Feld für Endzeichen 5.

Sehr irreführend, aber nun läuft es.

Danke euch!
 
Hi!

Wäre es dir möglich mir mal deinen Programmcode zu senden?
Ich hab nämlich auch noch ein Problem mit der Kommunikation, indem ich manchmal (sporadisch) keine Antwort vom Teilnehmer erhalte.
Nun würde ich gerne wissen, ob ich denn das Handling der Siemens-Bausteine wirklich richtig umgesetzt habe...

Vielen Dank!


Gruß,

Ottmar
 
Hi,

bitte nicht hauen für den Code, aber es war nur zum ausprobieren...
(und ich bin Neuling :p )

"Datenbaustein_1".Message ist ein String
"Datenbaustein_1".Buffer ist ein Array of Char

An den Eingängen meiner SPS ist das Kippschalter Tool.

Mit Schalter 0 kann ich nun einen Nachrichtenversand triggern und mit Kippschalter 1 die Nachrichten jede für sich aus dem Puffer holen.

Der Port ist 271 und ist in der Bausteinansicht konfiguriert mit Nachrichtenende durch 0x0d erkennen als Endzeichen 5.

Ansonsten ist nur noch die Baudrate und Leitungsvorbelegung eingestellt...


Code:
"In0_0_M_Old" := "In0_0_M";"In0_1_M_Old" := "In0_1_M";
"In0_7_M_Old" := "In0_7_M";


"In0_0_M" := "In0_0";
"In0_1_M" := "In0_1";
"In0_7_M" := "In0_7";



IF "In0_0_M" = TRUE AND "In0_0_M_Old" = FALSE THEN
  "Datenbaustein_1".Message := '#1$$$R';
  "Datenbaustein_1".RS_Length := 4;  
  "RS_SendReq" := TRUE;
END_IF;


IF "In0_1_M" = TRUE AND "In0_1_M_Old" = FALSE THEN
  "RS_RecReq" := TRUE;
  "RS_Received" := FALSE;
END_IF;


IF "In0_7_M" = TRUE AND "In0_7_M_Old" = FALSE THEN
  "Datenbaustein_1".temp[0] := '';

  FILL_BLK(IN:="Datenbaustein_1".temp[0],
         COUNT:=128,
         OUT=>"Datenbaustein_1".Buffer[0]);

END_IF;






IF "RS_SendReq" = TRUE THEN

  "SEND_PTP_DB"(REQ:=1,
                PORT:=271,
                BUFFER:="Datenbaustein_1".Message,
                DONE=> "RS_SendDone",
                LENGTH:="Datenbaustein_1".RS_Length
  );

  IF "RS_SendDone" = TRUE THEN
    "RS_SendReq" := FALSE;

    "SEND_PTP_DB"(REQ:=0,
                PORT:=271,
                BUFFER:="Datenbaustein_1".Message,
                DONE=> "RS_SendDone",
                LENGTH:="Datenbaustein_1".RS_Length
                );

  END_IF;
END_IF;


IF "RS_RecReq" = TRUE THEN

  "RCV_PTP_DB"(EN_R:=TRUE,
               PORT:=271,
               NDR=>"RCV_NDR",
               ERROR=>"RCV_ERROR",
               STATUS=>"RCV_STATUS",
               BUFFER:="Datenbaustein_1".Buffer,
               LENGTH=>"Datenbaustein_1".Length);

  IF "RCV_NDR" = TRUE THEN
    "RS_Received" := TRUE;
    "RS_RecReq" := FALSE;

    "RCV_PTP_DB"(EN_R:=FALSE,
             PORT:=271,
             NDR=>"RCV_NDR",
             ERROR=>"RCV_ERROR",
             STATUS=>"RCV_STATUS",
             BUFFER:="Datenbaustein_1".Buffer,
             LENGTH=>"Datenbaustein_1".Length);

  END_IF;
END_IF;
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Hi!

Ich danke dir für die schnelle Rückmeldung.

Das Problem kam nicht von meinem Code, sondern durch die Terminierung im BUS.
Diese habe ich am Modul vorgenommen und auch am letzten BUS-Teilnehmer.
Seit ich die Terminierung an der CPU abgeschaltet habe (TA und TB abgeklemmt) trat das Problem nicht mehr auf.

Die Nachrichten waren physikalisch auf dem BUS (Antwort vom Motor kam also), kamen nur in meinem Empfangspuffer nicht an.

Einen Unterschied zu deinem Code habe ich an der Stelle wo die Rückmeldung "NDR_RCV" verwendet wird.
Dort habe ich mal einer Quelle entnommen, dass der Baustein "RCV_PTP" an "NDR_RCV" meldet, wenn eine neue Nachricht eingegangen ist.
Erst dann soll mit "EN_R" die Nachricht aus dem Modul in den Puffer geholt werden. "NDR_RCV" liegt also direkt an "EN_R" an. So hab ich das und es funktioniert zuverlässig.

Alles in allem ist die Beschreibung der Bausteine aber mehr als schlecht.


Gruß,

Ottmar
 
Zuletzt bearbeitet:
da stimme ich dir zu, die beschreibung ist echt mies...

aber die idee mit ndr and en_r finde ich gut :)
nur mal schauen wie man das in scl schön umsetzen kann...
 
Zurück
Oben