Elegantes Füllen von Arrays (Netzwerk-Pakete)

OP #3726988
Lesenswert?
• ▲
▼
Guten Morgen,

ich bin dabei mir mit WinPCAP eigene Netzwerkpakete zusammenzusetzen, 
jedoch finde ich die jetzige Umsetzung etwas unschön und schwer zu 
warten.
1
char destination_mac[] = {0x01, 0x01, 0x01, 0x01, 0x01, 0x01};
2
char source_mac[] = {0x02, 0x02, 0x02, 0x02, 0x02, 0x02};
3
memcpy(&packet[0], destination_mac, 6);
4
memcpy(&packet[6], source_mac, 6);
5

6
/* Ehternet Frame */
7
packet[12] = 0x08; /* Type IP */
8
packet[13] = 0x00;
9
packet[14] = 0x45; /* Version and Header-length */
10
packet[15] = 0x00; /* Differentiated Services Field */
11
packet[16] = 0x00; /* Total length */
12
packet[17] = 0x34;
13
...

Hat jemand eine Empfehlung wie ich das eleganter lösen kann?

Dank und Gruß
Dennis
Persönliche Seite #3727035
Lesenswert?
• ▲
▼
Dennis S. schrieb:
> memcpy(&packet[0], destination_mac, 6);
> memcpy(&packet[6], source_mac, 6);
1
memcpy(packet, destination_mac, sizeof (destination_mac));
2
memcpy(packet + 6, source_mac, sizeof (source_mac));

Und das gleiche Konzept kannst Du natürlich auch für Dein Ethernet-Frame 
anwenden.
1
char ethernet_frame = {0x08, 0x00, 0x45, 0x00, 0x00, 0x34};
2

3
memcpy(packet + 12, ethernet_frame, sizeof (ethernet_frame));

Die numerischen Konstanten 0, 6 und 12 könntest Du natürlich auch noch 
durch #defines ersetzen:
1
#define OFFSET_DESTINATION_MAC 0
2
#define OFFSET_SOURCE_MAC 6
3
#define OFFSET_ETHERNET_FRAME 12
4

5
char destination_mac[] = {0x01, 0x01, 0x01, 0x01, 0x01, 0x01};
6
char source_mac[] = {0x02, 0x02, 0x02, 0x02, 0x02, 0x02};
7
char ethernet_frame = {0x08, 0x00, 0x45, 0x00, 0x00, 0x34};
8

9
memcpy(packet + OFFSET_DESTINATION_MAC, destination_mac, sizeof (destination_mac));
10
memcpy(packet + OFFSET_SOURCE_MAC, source_mac, sizeof (source_mac));
11
memcpy(packet + OFFSET_ETHERNET_FRAME, ethernet_frame, sizeof (ethernet_frame));
#3727503
Lesenswert?
• ▲
▼
Dennis S. schrieb:
> Rufus Τ. Firefly schrieb:
>> Vlad Tepesch schrieb:
>>> was spricht gegen die definition entsprechender structs?
>>
>> Vermutlich auch nichts, man muss nur aufpassen, daß diese gepackt
>> sind, wenn Datentypen > Byte darin verwendet werden - und dann auch auf
>> die Byte-Order.
>
> Das ist der Grund, warum ich das nicht gemacht habe..

Kein guter Grund.
Dazu gibt es in jedem noch so schmuftigen Compiler ein paar Pragmas, mit 
denen man packing erzwingen kann. Und wenn die Struktur letzten endes 
nur dazu dient, den unsigned chars aus dem Array einen Namen zu 
verpassen, so dass man nicht mehr
1
  packet[12] = 0x08; /* Type IP */
2
  packet[13] = 0x00;
3
  packet[14] = 0x45; /* Version and Header-length */
4
  packet[15] = 0x00; /* Differentiated Services Field */
5
  packet[16] = 0x00; /* Total length */
6
  packet[17] = 0x34;
schreiben muss, sondern (mit der Hilfe von ein paar enums oder Makros) 
schreiben kann
1
  packet.Type           = IP_TYPE;
2
  packet.VersionLength  = 69;
3
  packet.DiffServices   = 0
4
  packet.TotalLength    = 0;
5
  packet.SchiessMichTot = 52;

und das ist dann doch schon um einiges übersichtlicher, als die 
ursprüngliche Byteebene, in der eben alles einfach nur ein Byte war und 
man sich mit zusätzlichen Kommentaren behelfen mus, um zu wissen, was 
man da jetzt gerade eigentlich im Array befüllt.
Persönliche Seite #3727562
Lesenswert?
• ▲
▼
Karl Heinz schrieb:
>> Das ist der Grund, warum ich das nicht gemacht habe..
>
> Kein guter Grund.
> Dazu gibt es in jedem noch so schmuftigen Compiler ein paar Pragmas

Möglicherweise hat sich Dennis auf den Teil mit der Byte-Order 
bezogen, da muss man beim Befüllen der Struktur halt aufpassen 
(natürlich nur, sofern diese Datentypen > Byte enthält).
OP #3727841
Lesenswert?
• ▲
▼
Nein, nein es ging schon um das Packen der Struktur. Ich meine irgendwo 
mal gelesen zu haben, dass das auf einigen Systemen zu Problemen führen 
kann. Das Programm ist eigentlich auch nur ein "schneller" Hack deswegen 
mache ich es erstmal wie von Rufus beschrieben. Danke an alle.

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren