IPC Kommunikation zwischen mehreren Prozessen

Alles rund um die Programmierung mit Qt
Antworten
softwaremaker
Beiträge: 149
Registriert: 1. April 2009 19:25

IPC Kommunikation zwischen mehreren Prozessen

Beitrag von softwaremaker »

Ich möchte das meine Anwendung gleichzeitig mehrfach auf einem PC ausgeführt werden kann. Dabei sollen alle Prozesse (gleiche Anwendung) auf die selbe Datenbasis zugreifen. Ich möchte keine SQL-Datenbank benutzen, zwar wäre mit dieser das gleichzeitige Zugriffs-Problem auf die Daten behoben, da das DBMS sich darum kümmert, aber es soll halt keine DB sein.
Ich habe meine Daten in einer/mehreren Datei/en mit speziellem Format bzw. auch XML gespeichert. Die Anwendung soll lesen und schreiben können.
Mein Plan ist folgender:
- erster Prozess legt QSharedMemory an und da QSharedMemory::create true zurück gibt ist er der Server
- weitere Prozesse versuchen QSharedMemory::create zu machen, scheitern aber da bereits existiert, sie sind also ein Client
- über weitere QSharedMemory erfolgt die Kommunikation zwischen Server und Clients (Daten austauschen), denn nur der Server darf in die o.g. Dateien (XML) schreiben oder lesen (damit gibt es keine Probleme mit gleichzeitigem Zugriff auf die Dateien).

Meine Frage:
Gibt es einen besseren Weg (plattformunabhängig, ohne DBMS) bzw. bereits eine Lösung von Qt oder anderen? Denn es gibt folgende Nachteile:
- aufwendig zu realisieren, denn wenn Server beendet wird, soll ein Client die Server-Funktion übernehmen
- ich muss in der Anwendung mit einem Timer ständig in QSharedMemory prüfen, ob neue Daten vorhanden sind, keine Events bei QSharedMemory
- allgemein ist die ganze Kommunikationssteuerung sehr aufwendig
Mani99
Beiträge: 244
Registriert: 15. April 2009 10:46
Wohnort: München

Re: IPC Kommunikation zwischen mehreren Prozessen

Beitrag von Mani99 »

softwaremaker hat geschrieben: - aufwendig zu realisieren, denn wenn Server beendet wird, soll ein Client die Server-Funktion übernehmen
Wäre es eine möglichkeit mit einem timer zu prüfen ob der server prozess noch läuft? Oder per ping zu prüfen ob noch eine reaktion kommt?
softwaremaker hat geschrieben: - ich muss in der Anwendung mit einem Timer ständig in QSharedMemory prüfen, ob neue Daten vorhanden sind, keine Events bei QSharedMemory
Warum implementierst du nich selbst signals und slots? Ich weiß zwar nicht wie dein programm funktioniert, aber event. könnte dir das helfen!
softwaremaker
Beiträge: 149
Registriert: 1. April 2009 19:25

weiter1

Beitrag von softwaremaker »

Der Server teilt über QSharedMemory den Clients mit, dass er beendet wird und der 1.Client wird dann einfach zum Server (alles über QSharedMemory). Für den Fall dass der Server abschmiert und die ordnungsgemäße Übergabe nicht mehr durchgeführt wurde, muss ich natürlich noch eine QSharedMemory-Kommunikation realisieren, mit der die Clients auch prüfen, ob der Server noch antwortet, wenn nicht dann wird der 1.Client zum Server (es muss also auch eine Client-Liste geben =QSharedMemory).

Funktionieren Signal und Slot prozessübergreifend?
Ich könnte natürlich auch einiges über die Message-Funktion des Betriebssystems machen (Win: SendMessage), dann müsste ich nicht immer den QSharedMemory-Inhalt pollen. Damit könnte die Kommunikationssteuerung etwas einfacher werden.

Update: Später soll das Server-Client auch über Netzwerk laufen (QTcpSocket), jedoch auf dem PC verbindet sich nur der QSharedMemory-Server über das Netzwerk mit anderen, d.h. wenn die Anwendung mehrmals auf einem PC gestartet wird bleibt es bei nur einer Netzwerkverbindung, da die oben beschriebene QSharedMemory-Kommunikation erhalten bleibt.
softwaremaker
Beiträge: 149
Registriert: 1. April 2009 19:25

QLocalSocket

Beitrag von softwaremaker »

Hab mir ebend mal den Source von QtSingleApplication angeschaut und wohl eine bessere Möglichkeit als QSharedMemory gefunden:

QLocalServer bzw. QLocalSocket
(eine Art QTcpSocket nur Lokal über Named Pipe (Win))
pfid
Beiträge: 535
Registriert: 22. Februar 2008 16:59

Beitrag von pfid »

Wenn das so geht, wärs wohl die beste Lösung. Schnell, (vermutlich) eventgesteuert, und (hoffentlich) plattformunabhängig.
Bin per google nur auf den QTCPSocket und hunderte Vorschläge zum Thema MOM (*kotz*) gestoßen, daher wunderts mich dass es wohl doch eine so einfach und naheliegende Qt-Lösung gibt.

Schreib mal wie dus schlussendlich implementierst.
RHBaum
Beiträge: 1436
Registriert: 17. Juni 2005 09:58

Beitrag von RHBaum »

@pfid
Warum sollte es nicht gehen ?
Unter Linux sind Named Pipes schon immer eine feste groesse in der IPC Welt ... und wenn man weiss wonach man suchen muss, findet man in der windows API Doku auch die entsprechenden Abschnitte (mit dem Hinweis, das erst Windows XP bzw Windows NT Named Pipes koennen, windows 95 / 98 iss da aussen vor).
Man koennts also auch selbst programmieren, ohne QT, nur hat Trolltech schon mal schoen abstrahiert und auf mehrere Plattformen migriert.

Ausserdem sind sockets und pipes konzeptionell nicht so unterschiedlich .... die idee pipes ueber die allgemeinere socket schnittstelle abzufassen ist gar ned so abwegig. Unter Linux kann man IMHO sockets ueber bestehende pipes legen, oder es werden imho sogar transparent verbindungen ueber pipes realisiert, wenn man "localhost" nutzt.

@softwaremaker
Wenn es das ist was du willst ?
Shared Memory und pipes sind aber 2 ganz unterschiedliche schuhe ... man programmiert das sysntaktisch volkommen anders ... wenn du aber eh ne eventorientierte schnittstelle brauchst, klar sind pipes eh besser.

Aber ein punkt in deiner anforderung wird recht schwer/umstaendlich umzusetzen sein ...

ein client uebernimmt den server, und faellt der client aus ... springt nen anderer client ein ... das wird ned einfach ....

besser bzw einfacher waer:
erster client startet den server mit ....
der server merkt sich welche clients verbunden sind
hat sicher der letzte client abgemeldet, bzw reagiert ned mehr ... faehrt auch der server von allein runter ...

Ciao ...
upsala
Beiträge: 3946
Registriert: 5. Februar 2006 20:52
Wohnort: Landshut
Kontaktdaten:

Beitrag von upsala »

2 Anwendungen benutzen deine Dateien über ein Netzlaufwerk. Was machst du jetzt?

Btw.: Ist QSharedMemory unter Unix eigentlich Benutzerübergreifen?
softwaremaker
Beiträge: 149
Registriert: 1. April 2009 19:25

File Locking

Beitrag von softwaremaker »

@upsala: man müsste trotzdem mit QtLockedFile arbeiten um den gleichzeitigen Zugriff übers Netzwerk zu verhindern. Die Netzwerk-Kommunikation wollte ich mit QTcpSocket realisieren, d.h. nicht mit Netzlaufwerkfreigaben und Dateien.
Was würdest du empfehlen?
upsala
Beiträge: 3946
Registriert: 5. Februar 2006 20:52
Wohnort: Landshut
Kontaktdaten:

Beitrag von upsala »

Ich würde eine Datenbank verwenden, und weis eigentlich nur sehr wenig Argumente gegen eine DB. Aber das ist nicht der Punkt.

Ich wollte dich nur auf mögliche Probleme hinweisen.
pfid
Beiträge: 535
Registriert: 22. Februar 2008 16:59

Beitrag von pfid »

RHBaum hat geschrieben:@pfid
Warum sollte es nicht gehen ?
Unter Linux sind Named Pipes schon immer eine feste groesse in der IPC Welt ... und wenn man weiss wonach man suchen muss, findet man in der windows API Doku auch die entsprechenden Abschnitte (mit dem Hinweis, das erst Windows XP bzw Windows NT Named Pipes koennen, windows 95 / 98 iss da aussen vor).
Man koennts also auch selbst programmieren, ohne QT, nur hat Trolltech schon mal schoen abstrahiert und auf mehrere Plattformen migriert.

Ausserdem sind sockets und pipes konzeptionell nicht so unterschiedlich .... die idee pipes ueber die allgemeinere socket schnittstelle abzufassen ist gar ned so abwegig. Unter Linux kann man IMHO sockets ueber bestehende pipes legen, oder es werden imho sogar transparent verbindungen ueber pipes realisiert, wenn man "localhost" nutzt.
Ja, das ist mir schon klar. Ich wollte eher meine Überraschung ausdrücken, dass es entgegen meiner (kurzen) Suche in Doku und google eben doch einen Qt Weg gibt :)
RHBaum
Beiträge: 1436
Registriert: 17. Juni 2005 09:58

Beitrag von RHBaum »

Naja gibt schon einige Argumente gegen eine DB ...

wenn seine vorgabe XML ist:
SQLite oder nen andere filebasierte db system - umweg ueber das SQLInterface, dafuer aber abstrahierter locking mechanismus auf dateiebene. Weiss ned ob der overhaed sich deswegen lohnt.

Ist das XML diskutabel, ist sqlite sicher ne Überlegung wert.

Performance ....
ist das nen problem, wird er mit ner datenbank ned weit kommen ....
das schnellste ist Shared Memory, die mutter aller IPC techniken.
Danach kommen lokale pipes ...

In sachen benutzer-freundlichkeit iss die DB Loesung natuerlich weit vorn ... und den code wird man schnell verstehen und ist damit leichter wartbar.

Fertigerere Loesungen wird er kaum finden ....
überlegt man in richtigung allgemeine IPC technik, hat man meist ganz spezielle definierte wuensche, die sich mit nem generellen ansatz kaum erschlagen lassen ....
IPC Aufsaetze mit generellerem Ansatz:
Unter windows ist COM immer noch ne blick wert ....
unter linux gabs doch mal dcop ... gibts da noch was ?
dbus ist das neuere Modell, aber das unter windows zum laufen zu bringen ....
RPC generell ... ist aber schon fast zu low level ...
Dann gehen mir auch schon die Ideen aus ...

Ciao ...
Antworten