Moin,
Ich habe nun in Gwen den letzten noch fehlenden Part - den IPC Code - auf den
neuen Netzwerk-Code umgestellt. Das laeuft somit inzwischen auch mit dem
bisher einzigen Client/Server des IPC-Codes: Libchipcard2.
Neuer Code fuer Interprocess Communication (IPC)
=========================================
Der alte IPC-Code war festgelegt darauf, ueber HTTP gefahren zu werden.
In Libchipcard2 wird auch weiterhin HTTP verwendet, aber das ist nun nicht
mehr Vorraussetzung. Der neue Code kann IPC grundsaetzlich ueber jede Art von
GWEN_NetLayer betreiben bleibt aber weitgehend Source-kompatibel zum alten
Code (bis auf das Handling von Verbindungen).
Dafuer habe ich nun einen neuen NetLayer hinzugefuegt, der die Arbeit mit
Paket-ortientierten Protokollen stark vereinfacht: GWEN_NetLayerPackets (kann
auch zu anderen Zwecken ausser IPC verwendet werden).
Dieser NetLayer kann nun ausgehende Pakete in eine Warteschlange einreihen und
nacheinander versenden, und genauso reiht er empfangene Pakete in eine andere
Warteschlange ein.
So braucht beispielsweise der IPC-Code nur noch die Kommandos in einen Puffer
schreiben, daraus ein GWEN_NL_PACKET zu erstellen (zwei Aufrufe) und dieses
Paket in die Warteschlange stellen.
Das praktische am neuen NetLayer ist, dass er nicht *nur* ueber
Paket-orientierte Protokolle laeuft, sondern grundsaetzlich ueber alle
GWEN_NetLayer laufen kann.
GWEN_NetLayer in Paket-orientierten Protokollen
========================================
Der generelle Ablauf beim Versenden von Daten ueber einen NetLayer ist dieser:
- GWEN_NetLayer_BeginOutPacket()
- GWEN_NetLayer_Write() [solange Daten zu senden sind]
- GWEN_NetLayer_EndOutPacket()
Im GWEN_NetLayerHttp wird beispielsweise beim ersten Aufruf die Kommando-Zeile
erzeugt (z.B. "GET / HTTP/1.1") sowie die Header ("Content-Length: 123" etc).
Diese werden dann in den darunterliegenden GWEN_NetLayer (meist
GWEN_NetLayerSocket oder Ssl) geschrieben. Sobald die Kommandozeile und der
Header geschrieben sind, werden die Daten, die ueber GWEN_NetLayer_Write()
uebergeben werden, hinterhergesendet.
Bei GWEN_NetLayerEndOutPacket() wird dann lediglich der Puffer geflushed sowie
alles fuer das naechste Paket vorbereitet.
Diese Vorgehensweise hat grosse Vorteile: Man muss nur noch einmal zu Beginn
ein NetLayer-spezifisches Setup machen (beispielsweise die Zieladresse fuer
eine Verbindung angeben, bei HTTP eventuell ein paar Header vorbesetzen), und
ab da ist der Ablauf beim Versenden eines Paketes fuer jeden NetLayer gleich.
Nur dadurch ist es moeglich, dass bisher alle NetLayer beliebig miteinander
stapelbar sind, ohne dass ein NetLayer sich mit dem jeweils darunterliegenden
auskennen muss.
GWEN_NetLayer in nicht-Paket-orientierten Protokollen
============================================
Was aber passiert bei nicht-Paket-orientierten Protokollen?
In diesem Fall sind die (virtuellen) Funktionen GWEN_NetLayer_BeginOutPacket()
und EndOutPacket() nicht gesetzt und geben stattdessen einen speziellen
Fehlercode zurueck, der besagt, dass diese Funktion nicht unterstuetzt wird
(GWEN_ERROR_UNSUPPORTED).
An diesem Fehlercode erkennt der Aufrufer - meist der drueberliegende NetLayer
- dass es sich *nicht* um einen Netzwerkfehler handelt und ignoriert diese
Meldung (setzt also seine Arbeit einfach fort).
Der Trick ist also: So ziemlich jeder GWEN_NetLayer (ausser Socket und Ssl)
verhaelt sich so, als ob sich unter ihm ein Paket-orientierter NetLayer
befaende. Ist das mal nicht der Fall, macht das auch nichts, weil in dem Fall
ja die Daten einfach so roh, wie sie bei GWEN_NetLayer_Write() uebergeben
werden, geschrieben werden koennen.
Synchrone vs asynchrone Netzwerk-Funktionen
======================================
Mit seinen vergleichsweise wenigen Funktionen aber dennoch grossen
Flexibilitaet ist daher der neue GWEN_NetLayer-Code deutlich dem alten Ansatz
von frueheren Gwen-Version ueberlegen.
Der neue Code ist dabei immer noch vollstaendig asynchron angelegt (was fuer
Single-Thread-Server wie Libchipcard2 notwendig ist), hat aber zusaetzlich
synchrone Funktionen, die von Clients gerne verwendet werden.
Diese synchronen Funktionen (zu erkennen am _Wait() am Ende des
Funktionsnamens) muessen aber nicht von jedem einzelnen NetLayer
implementiert werden, sondern werden von der Basisklasse zur Verfuegung
gestellt.
Das vereinfacht das Erstellen von neuen NetLayern sehr, denn diese muessen nur
eine Handvoll Funktionen implementieren, bieten aber dennoch einen grossen
Leistungsumfang.
Gruss
Martin
--
"Things are only impossible until they're not"
AqBanking - http://www.aquamaniac.de/aqbanking/
LibChipcard - http://www.libchipcard.de/
-------------------------------------------------------
SF.Net email is sponsored by:
Tame your development challenges with Apache's Geronimo App Server. Download
it for free - -and be entered to win a 42" plasma tv or your very own
Sony(tm)PSP. Click here to play: http://sourceforge.net/geronimo.php
_______________________________________________
Aqbanking-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/aqbanking-devel