Wireshark Plugin für S7-Protokoll

Zuviel Werbung?
-> Hier kostenlos registrieren
Hallo,

nachdem ich das Thema schon eine Zeit verfolge und auch versucht habe das 0x72 Protokol zu verstehen, möchte ich nun meine Ergebnisse einbringen:

Berechnung Session ID:
Zuminstes das letzte Byte der Session ID wird aus dem Byte 17 der Resopnse auf Start Session berechnet -> Byte 18 + 0x80

Code:
Response auf Start Session:

0000   72 01 00 7a 32 00 00 04 ca 00 00 00 01 36 11 02
0010   87 [B]20[/B] 87 53 a1 00 00 01 20 82 1f 00 00 a3 81 69
0020   00 15 00 a3 82 32 00 17 00 00 01 3a 82 3b 00 04
0030   82 00 82 3c 00 04 81 40 82 3d 00 04 84 80 c0 40
0040   82 3e 00 04 84 80 c0 40 82 3f 00 15 1b 31 3b 36
0050   45 53 37 20 32 31 34 2d 31 41 45 33 30 2d 30 58
0060   42 30 20 3b 56 32 2e 32 82 40 00 15 05 32 3b 37
0070   39 34 82 41 00 03 00 03 00 a2 00 00 00 00 72 01
0080   00 00

=> 0x20 + 0x80 = a0

Request Write:
0000   72 02 00 66 31 00 00 05 42 00 00 00 02 00 00 03
0010   [B]a0[/B] 34 00 00 03 a0 01 01 82 32 01 00 17 00 00 01
0020   3a 82 3b 00 04 82 00 82 3c 00 04 81 40 82 3d 00
0030   04 84 80 c1 00 82 3e 00 04 84 80 c0 40 82 3f 00
0040   15 00 82 40 00 15 00 82 41 00 03 00 03 00 00 00
0050   00 04 e8 89 69 00 12 00 00 00 00 89 6a 00 13 00
0060   89 6b 00 04 00 00 00 00 00 00 72 02 00 00

Was ich bis heute nicht geschafft habe ist die SYM-CRC Berechnung erfolgreich durchzuführen. Weiß jemand mehr darüber?
 
Berechnung Session ID:
Zuminstes das letzte Byte der Session ID wird aus dem Byte 17 der Resopnse auf Start Session berechnet -> Byte 18 + 0x80
Für das eine Byte scheint das ja schonmal zu passen.
Liegt natürlich in dem Datenteil der irgendwie keiner Struktur zu folgen scheint.

Was ich bis heute nicht geschafft habe ist die SYM-CRC Berechnung erfolgreich durchzuführen. Weiß jemand mehr darüber?

Siemens nutzt das gleiche Generatorpolynom wie auch beim Profibus, nämlich:
x^32+x^31+x^30+x^29+x^28+x^26+x^23+x^21+x^19+x^18+x^15+x^14+x^13+x^12+x^9+x^8+x^4+x+1

Das hat der Jochen auch schon in seiner Lib drin, funktioniert einwandfrei:
https://github.com/jogibear9988/Dot...DaveConnectionLibrary/General/TiaCrcHelper.cs
 
Ich habe nochmal meine Logfiles durchgesehen. Der variable Teil in der Session-Id scheint nur das rechte Byte zu sein, zumindest steht in dem Byte davor immer eine 3.
Wenn man die Daten an Wort-Grenzen ausrichtet gehört die 3 zur Id, muss aber nicht sein.
Aber da beim Verbindungsabbau auch die Session-Id inkl. der 3 im Datenteil vorhanden ist, würde ich sagen sie gehört mit dazu.
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Siemens nutzt das gleiche Generatorpolynom wie auch beim Profibus, nämlich:
x^32+x^31+x^30+x^29+x^28+x^26+x^23+x^21+x^19+x^18+x^15+x^14+x^13+x^12+x^9+x^8+x^4+x+1

Das hat der Jochen auch schon in seiner Lib drin, funktioniert einwandfrei:
https://github.com/jogibear9988/Dot...DaveConnectionLibrary/General/TiaCrcHelper.cs

Danke für den Tipp, muss ich mir mal genauer anschauen.

Ich habe nochmal meine Logfiles durchgesehen. Der variable Teil in der Session-Id scheint nur das rechte Byte zu sein, zumindest steht in dem Byte davor immer eine 3.
Wenn man die Daten an Wort-Grenzen ausrichtet gehört die 3 zur Id, muss aber nicht sein.
Aber da beim Verbindungsabbau auch die Session-Id inkl. der 3 im Datenteil vorhanden ist, würde ich sagen sie gehört mit dazu.

Bei mir steht im Byte davor auch immer eine 3.

Ich habe deine und meine Start Session Response verglichen (sind leider beides 1214c) folgendes kommt dabei raus:
comp_res.gif
 
Zuletzt bearbeitet:
Hallo,

Das Posting ist zwar schon etwas älter, aber vieleicht erinnert sich noch jemand:

Könnte ja sein, das die mittleren 4 bytes der crc sind welcher in dem Patent beschrieben ist? Die ersten 4 Bytes Speicherbereich? Oder etwas in die Richtung und die letzten 4 Bytes die laufende ID... Sind aber alles nur Ideen...

Welches Patent meint Ihr hier?
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Hallo,

mir ist noch nicht klar, worüber die Sym-CRC bei der S7-1500 berechnet wird. Und ob diese Sym-CRC Berechnung auch für die S7-1500 unterstützt wird.
Aus einem TIA Projekt kann ich zum Beispiel folgendes herausziehen:
<dataBlock name="DB6" logicalAddress="%DB6" supportsAddressingByOffset="false" subtype="DB" CRC="0xD4FD3326">
...
<dataTag name="Array_Byte" offset="32.0" datatype="Array[0..10] of Byte" id="60" lid="22" rid="0x02010002" />
...
<dataTag name="IEC_COUNTER" offset="148.0" datatype="IEC_COUNTER" id="89" lid="67" rid="0x0200001E" subPartIndex="-5" />
...
<dataTag name="IEC_LTIMER" offset="190.0" datatype="IEC_LTIMER" id="92" lid="70" rid="0x02000044" subPartIndex="-8" />

In einem Wireshark-Mitschnitt, einer Abfrage der Daten aus DB6 sehe ich unter anderem:
Item Address: SYM-CRC=8db85e63, LID=DB6.22

Weiß jemand, ob und wie sich aus den Daten oben berechnen lässt?

BTW: Mit dem .xml File und dem Wireshark-Mitschnitt habe ich die im S/COMM-Plus Wireshark Plugin noch unbekannten Typen
0x10 = IEC_COUNTER
und
0x11 = IEC_LTIMER
gefunden.


Gruß
Jürgen
 
Hallo,

mir ist noch nicht klar, worüber die Sym-CRC bei der S7-1500 berechnet wird. Und ob diese Sym-CRC Berechnung auch für die S7-1500 unterstützt wird.
Aus einem TIA Projekt kann ich zum Beispiel folgendes herausziehen:
<dataBlock name="DB6" logicalAddress="%DB6" supportsAddressingByOffset="false" subtype="DB" CRC="0xD4FD3326">
...
<dataTag name="Array_Byte" offset="32.0" datatype="Array[0..10] of Byte" id="60" lid="22" rid="0x02010002" />
...
<dataTag name="IEC_COUNTER" offset="148.0" datatype="IEC_COUNTER" id="89" lid="67" rid="0x0200001E" subPartIndex="-5" />
...
<dataTag name="IEC_LTIMER" offset="190.0" datatype="IEC_LTIMER" id="92" lid="70" rid="0x02000044" subPartIndex="-8" />

In einem Wireshark-Mitschnitt, einer Abfrage der Daten aus DB6 sehe ich unter anderem:
Item Address: SYM-CRC=8db85e63, LID=DB6.22

Weiß jemand, ob und wie sich aus den Daten oben berechnen lässt?

BTW: Mit dem .xml File und dem Wireshark-Mitschnitt habe ich die im S/COMM-Plus Wireshark Plugin noch unbekannten Typen
0x10 = IEC_COUNTER
und
0x11 = IEC_LTIMER
gefunden.


Gruß
Jürgen

Also für die 1200er hab ich Code in der Klasse TiaCrcHelper, ob das aber auch für die 1500er funktioniert weiß ich nicht... https://github.com/jogibear9988/DotNetSiemensPLCToolBoxLibrary
 
mir ist noch nicht klar, worüber die Sym-CRC bei der S7-1500 berechnet wird. Und ob diese Sym-CRC Berechnung auch für die S7-1500 unterstützt wird.
Aus einem TIA Projekt kann ich zum Beispiel folgendes herausziehen:
<dataBlock name="DB6" logicalAddress="%DB6" supportsAddressingByOffset="false" subtype="DB" CRC="0xD4FD3326">
...
<dataTag name="Array_Byte" offset="32.0" datatype="Array[0..10] of Byte" id="60" lid="22" rid="0x02010002" />
...
<dataTag name="IEC_COUNTER" offset="148.0" datatype="IEC_COUNTER" id="89" lid="67" rid="0x0200001E" subPartIndex="-5" />
...
<dataTag name="IEC_LTIMER" offset="190.0" datatype="IEC_LTIMER" id="92" lid="70" rid="0x02000044" subPartIndex="-8" />

In einem Wireshark-Mitschnitt, einer Abfrage der Daten aus DB6 sehe ich unter anderem:
Item Address: SYM-CRC=8db85e63, LID=DB6.22

Weiß jemand, ob und wie sich aus den Daten oben berechnen lässt?

Bei der 1200 hätte ich gesagt, mit LID=22 wird die Variable "Array_Byte" gelesen. D.h du müsstest die CRC aus dem Symbol "Array_Byte" bilden. Wenn ich das so mache wie für die 1200 kommt aber ein anderer Wert heraus.
Was für Daten werden denn mit deinem abgehörten CRC/LID gelesen?

Bei der 1200 kann man überhaupt kein komplettes Array lesen, zumindest nicht mit einem Basic-Panel, dort lassen sich nur einzelne Array-Elemente lesen. In dem Fall folgt nach der LID noch der Array-Index. Als die symbolische Adressierung noch in den 0x32er Telegrammen verpackt war, gab es pro LID zusätzlich ein Byte mit Flags, die kennzeichneten auf welchen LID-Typ zugegriffen wurde. Man hat aber wohl festgestellt dass die Kombination aus CRC und LID schon eindeutig ist und dieses Flag-Byte dann entfernt. Denn über die LID weiß der Partner schon dass es sich in einem Array, Struct oder sonstiges befindet.

BTW: Mit dem .xml File und dem Wireshark-Mitschnitt habe ich die im S/COMM-Plus Wireshark Plugin noch unbekannten Typen
0x10 = IEC_COUNTER
und
0x11 = IEC_LTIMER
gefunden.

a) Was für ein xml File?
b) Wenn ich in einem DB eine Variable von Typ "IEC_COUNTER" anlege, ist das eine Struktur. Was liest das HMI wenn es ein Typ "IEC_COUNTER" liest? Alle Elemente, oder nur ein einziges? Bei TIA-V12 kann ich so eine Variable überhaupt nicht anlegen.

Mir steht keine 1500 zum Testen zur Verfügung, falls das alles 1500-spezifisch sein sollte.
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Ich habe mir das mit der CRC-Berechnung auch bei der 1200er angesehen.
Bisher habe ich mir das entweder bei Merkervariablen oder bei Variablen dir direkt in einem DB liegen (z.B. DB99.VAR) angesehen. In den beiden Fällen wird die CRC einzig und allein aus dem Symbol berechnet.
Liegt die Variable aber beispielsweise innerhalb einer Struktur eines DBs, z.B. DB.STRUCT.VAR, dann gibt es eine andere CRC.

Naheliegend wäre es die aus dem kompletten Symbol zu bilden, also "STRUCT.VAR" mit dem "." als Trennzeichen. Passt nicht. Ein "/" als Trennzeichen probiert, passt auch nicht.

Kleines Such-Skript geschrieben:
Code:
public static void SucheCrcTrenner()
{
    bool found = false;
    byte[] bytes1 = Encoding.ASCII.GetBytes("VAR_STRUCT1");
    byte[] bytes2 = Encoding.ASCII.GetBytes("VAR_STRUCT1_INT");
    byte[] delim = { 0x00 };

    byte[] combined = bytes1.Concat(delim).Concat(bytes2).ToArray();

    int delim_pos = bytes1.Length;

    string search_crc = "b1c00672";
    string crc;

    search_crc = search_crc.ToUpper();

    for (byte i = 0; i < 255; i++)
    {
        combined[delim_pos] = i;
        crc = getcrc(combined).ToString("X").PadLeft(8, '0');
        if (crc == search_crc)
        {
            Console.WriteLine("Gefunden! Trennzeichen = " + i);
            found = true;
            break;
        }
    }
    if (!found)
    {
        Console.WriteLine("Nicht gefunden");
    }
    Console.ReadKey();
}

Das Trennzeichen ist 0x09.

D.h. bei einer 1200 gilt für eine Variable im DB: DB.STRUCT.VAR, die CRC über den Namen der "STRUCT" plus 0x09 plus Namen der "VAR" zu bilden.
Siemens hätte so schön ein "." nehmen können, aber das wäre wohl zu naheliegend gewesen.
 
@Thomas_v2.1,

hallo Thomas, ich setze dein Plugin seit einiger Zeit ein und es hat mir immer gute Dienste geleistet.
Danke schön für dieses hervorragende Tool.

Verbesserungswunscht, bezüglich nicht erkanntem "AnyPointer":
Es gibt zum datensatz Les4en/Schreiben "erweiterte AnyPojnter" evtl ist dir das bisher nicht bekannt.
Eben wollte ich was untersuchen, dabei kam diese "Schwäche" wieder mal zum Vorschein.
Daher sende ich dir Info, womit du das Implementieren kannst:

Ich versuch ert mal mit einem kommentierten HexDump:

Datensatz schreiben, z.B. an eine Profibus Teilnehmer

PG --> CPU 32 01 00 00 04 00 00 0e 00 08
05 01 Write, 1 Tag
12 0a
10 03 00 04 00 ff 01 00 07 fb
## ##### ##### ## #####--------- Logische Adresse
| | | +------------------ Kennung für Datensatz
| | +----------------------- Datensatz Nummer
| +--------------------------- Anzahl Elemente
+--------------------------------- Element Typ Char (so liest der simatic Manager)
ff 09 00 04 Datenkennung ... ganz normal
08 00 fd e8 Nutzdaten

CPU --> PG 32 03 00 00 04 00 00 02 00 01 00 00 Antwort
#####--- Retval OK
05 01 ff Alles OK.


Datensatz lesen

PG --> CPU 32 01 00 00 05 00 00 0e 00 00
04 01 Lesen, 1 Tag
12 0a
10 03 00 44 00 ff 01 00 07 fb
## ##### ##### ## #####--------- Logische Adresse
| | | +------------------ Kennung für Datensatz
| | +----------------------- Datensatz Nummer
| +--------------------------- Anzahl Elemente
+--------------------------------- Element Typ Char (so liest der simatic Manager)


CPU --> PG 32 03 00 00 05 00 00 02 00 48 00 00
04 01 Lesen, 1 Tag
ff 04 02 20 Nutzdaten Zählung in Bit
08 00 fd e8 00 00 ... Nutzdaten ...


Das kann jede normale S7-CPU, sowohl für lokal 300er Module,
oder für Profibus, bzw. Profinet Module, bzw. deren datensätze.

Der "AnyPointer" siehr wie folgt aus:

10 03 nn nn dd dd 01 00 aa aa

10 ist die normale Kennung
03 ist der Elementtyp, evtl. gehen auch andere, aber 03 ist üblich.
nn nn ist die Anzahl der Elemente, überlicherweise char, d.h. Bytes
dd dd Datensatz Nummer
01 ist die Kennung für Datensatz bei disem "speziellen AnyPointer"
aa aa ist die logische Adresse für Eingänge), bei Ausgängen wird 0x8000
aufadddiert, oder umgekehrt, genau wie beim SFB52

Das war es schon, Implementierung sollte kein großes Problem sein.


mfG. klaly






 
Zuletzt bearbeitet:
So ein "Mist",

ich krieg die Formatierung im Hexdump nicht hin.
Im Edit Feld sieht es immer gut aus, dann wirft das Forum aber scheinbar die "überflüssigen"
Leerzeichen wieder raus und es siehr "blöd" aus.

Ich bitte um Entschuldigung.
Es ist aber hoffentlich zu erkennen was die Felder bedeuten.

mfG. klaly
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Hi,
womit werden denn solche Telegramme erzeugt? Ich würde mir das gerne mal selber ansehen wenn möglich. Oder falls du eine Logdatei hast, wäre es nicht schlecht wenn du diese mal anhängst.

Nach dem was du oben geschrieben hast, sehe ich keinen Anhaltspunkt um den Aufbau vom S7-ANY zu unterscheiden. Die Kennungswerte für eine Variablenadresse sind demnach identisch:
0x12 = Variablenspezifikation
0x0a = Länge der folgenden Spezifikation in Bytes
0x10 = Syntax-ID, 0x10 steht für S7-Any-Pointer

Bei allem was danach folgt gehe ich davon aus dass es sich um einen S7-Any-Pointer handelt.

Alles andere was ich bisher an Adressformaten gesehen habe, geben auch eine andere Syntax-ID mit.
 
.
So ein "Mist",

ich krieg die Formatierung im Hexdump nicht hin.
Im Edit Feld sieht es immer gut aus, dann wirft das Forum aber scheinbar die "überflüssigen"
Leerzeichen wieder raus und es siehr "blöd" aus.

Ich bitte um Entschuldigung.
Es ist aber hoffentlich zu erkennen was die Felder bedeuten.

mfG. klaly


Vielleicht hilft dir die Benutzung der "CodeTags (#)" mit dem Doppelkreuz bei deiner Antwort weiter.
.
 
So wie es aussieht müsste ich die Bereichskennung 0x01 an der Position, an der bei einer normalen S7-Adresse z.B. 0x84 für den Bereich Datenbausteine steht, ergänzen. Dort dürfte momentan "unknown area" angezeigt werden.
Dann wäre der Aufbau prinzipiell gleich mit den S7-Any Pointer, wenn ich annehme dass die Adresse ebenfalls 3 und nicht nur 2 Bytes beinhaltet. Die Datenbausteinnummer wäre in den Fall die Datensatznummer (Dataset number).

Mach doch mal einen Vorschlag wie ich die Adresse in Textform in Wireshark darstellen soll.
Also z.B.:
Code:
Item[1]: (Dataset 256 Address 2043 CHAR 68)
- Variable specification: 0x12
- Length of following address specification: 10
- Syntax Id: S7ANY (0x10)
- Transport size: CHAR (3)
- Length: 68
- Dataset number: 256
- Area: Dataset (0x01)
- Address: 0x0007fb

Ich weiß überhaupt nicht wozu diese Adressierung benutzt wird.

Die Antworttelegramme sollten doch schon korrekt dekodiert werden können oder?
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Hi SoftMachine,

danke. Leider schreibe ich so selten im Forum, so dass ich diese "Feinheiten" leider nicht kannte.
Ich hatte meinen Text "schön" auf Courier umgestellt, schön formatier, abgesvhickt. Hmm, ...
Nochmal edititiert, das gleiche wieder, dann hatte ich keine Lust mehr.

mfG. klaly
 
@Thomas_v2.1,

du bekommst solche Telegramme, wenn du im HW-Konfigurator in der online Ansicht auf Profibus DP-V1 oder Profinet Teilnehmer, bzw. der Untereigenschaften klickst. Da werden dann nicht nur SZLs, sondern auch Datensätze gelesen.

Mal schaun was ich da zusammen klicken kann, dann schneide ich mit Wireshark mal ein paar Telegramme mit.

Oder wenn du bei einem lokal gesteckten Analogmodul den Diagnosestatus sehen willst, dann werden da auch Datensätze gelesen.

Das war jetzt gar nicht so einfach zu konstruieren.
Zuerst wollte ich die Drahtbrucherkennung eines Ananlogmoduls, z.B. 332-5HD01 dafür her nehmen.
Aber da wird von der Onlineansicht des HW-Konfigurator, nur eine entsprechende SZL gelesen, welche die CPU dann
in eine DS-Lesen Anfrage am Rückwandbus umsetzt. Das sind die Datensätze 1 und 2, welche z.B. auch mit dem SFB52 gelsen werden können.

War wohl nix.
Dann habe ich es mit einem CP341 versucht, da geht es.
Der muss z.B. lokal an der CPU hängen, ginge aber auch über Profibuis ET200M über Profinet auch ET200M.
Wenn du in der HW-Konfig die Online Ansicht auf machst und dann auf den CP341 doppelklickst, dann bekommst du den
Baugruppenzustand des CP341, da steht auch sein Name drin. Diesen wird über DS-Lesen geholt.

siehe folgenden Screenshot und Wireshark Aufzeichnung.
Ich vermute, das Hochladen der Anhänge macht mir Probleme (Firefox), mal schaun.

mfG. klaly
 
Zurück
Oben