Hallo zusammen,
ich versuche gerade ein TI Sitara StarerWare Ethernet Beispiel Projekt
von TCP auf UDP umzubauen um eine Kommunikation zu MATLAB aufzubauen.
Das ist meine erste Begenung mit lwip und "ernsthafter" Programmierung
einer Netzwerkschnittstelle, bisherige Erfahrungen stützen sich nur auf
die nutzung der Arduino/Energia UDP Funktionen.
Ich habe die lwip rawApi Dokumentation gelesen, versucht so weit es geht
das TCP Beispiel welches ich hier hatte nachzuvollziehen und habe mir
mal den Inhalt von EthernetUDP.cpp aus Energia angesehen, um zu sehen
wie die das dort lösen. Auch diverse Websiten zu dem Thema habe ich
überflogen.
In letzterer habe ich die Implementierung der do_recv Funktion nicht
komplett verstanden. Warum wird der arg Zeiger in einen Zeiger
EthernetUDP Zeiger gecastet und dann auf dessen Inhalt zugegriffen -
werden dafür nicht die ganzen restlichen Übergabewerte genutzt?
Wie dem auch sei, was ich meine Verstanden zu haben ist folgender Ablauf
(meine Implementierung der Schritte jeweils dahinter), mit dem ich erst
mal eine Grundsätzliche Reaktion auf ein empfangenes UDP Paket sehen
möchte:
- einen lwip Port anlegen:
- den Ethernetcontroller der Hardware initialisieren:
1 | EVMPortRGMIIModeSelect(); EVMMACAddrGet(0, lwipIfPort.macArray);
|
- lwip mit diesem Port initialisieren und in meinem Fall DHCP aktivieren
1 | lwipIfPort.instNum = 0;
|
2 | lwipIfPort.ipAddr = 0;
|
3 | lwipIfPort.netMask = 0;
|
4 | lwipIfPort.gwAddr = 0;
|
5 | lwipIfPort.ipMode = IPADDR_USE_DHCP;
|
6 |
|
7 | ipAddr = lwIPInit(&lwipIfPort);
|
- ein lwip pcb anlegen
1 | struct udp_pcb *toMatlabUDP; toMatlabUDP=udp_new();
|
- eine IP Adresse anlegen
1 | struct ip_addr janosMacIP; IP4_ADDR(&janosMacIP, 192, 167, 1, 103);
|
- zuweisen auf welche IP an welchem Eingangsport reagiert werden soll:
1 | err=udp_bind(toMatlabUDP, &janosMacIP, 5050);
|
2 | if(err==ERR_OK){
|
3 | ConsoleUtilsPrintf("udp bind erfolgreich ausgefuehrt \n\r" );
|
4 | }
|
5 | else{
|
6 | ConsoleUtilsPrintf("udp bind nicht ausgefuehrt \n\r" );
|
7 | }
|
- zuweisen, welche Funktion aufgerufen werden soll, wenn etwas über die
zuvor eingerichtete Verbindung eintrifft:
1 | udp_recv(toMatlabUDP, (udp_recv_fn)incommingUDP, NULL);
|
- eine Funktion schreiben, die dann die weitere Datenverarbeitung
übernimmt:
1 | err_t incommingUDP(void *arg, struct udp_pcb *upcb, struct pbuf *p, struct ip_addr *addr, u16_t port){
|
2 | ConsoleUtilsPrintf("incommingUDP aufgerufen \n\r" );
|
3 | pbuf_free(p);
|
4 | return ERR_OK;
|
5 | }
|
Was funktioniert:
IP Adresse wird zugewiesen, udp_bind gibt ERR_OK zurück, das Board
reagiert auf einen Ping.
Was nicht funktioniert: Das senden eines UDP Pakets aus MATLAB an den
Port und die IP des Boards schlägt fehl. In Wireshark sehe ich das
ausgehende UDP Paket vom PC an das Board und darauf die Antwort
1 | Destination Unreachable (Port unreachable)
|
. Die Funktion incommingUDP wird nicht aufgerufen.
Was habe ich also falsch gemacht?
Was grundsätzlich unklar ist: Auf welchem Mechanismus basiert der Aufruf
meiner incommingUDP Funktion durch lwip eigentlich? Wird der Ethernet
Adapter gepollt, löst er bei einem eintreffenden Paket einen Interrupt
aus und lwip stellt die Interrupt Service Routine, oder wie läuft das?
Irgendwie so muss es laufen, aber auch diesen Punkt konnte ich im schon
laufenden TCP Beispiel bisher nicht im Code finden.
Ich freue mich auf etwas Hilfe!