Mehrfachausführen der Applikation unter Linux/Unix verhinder

Alles rund um die Programmierung mit Qt
Antworten
gerome69
Beiträge: 188
Registriert: 28. April 2006 22:50
Wohnort: Berlin
Kontaktdaten:

Mehrfachausführen der Applikation unter Linux/Unix verhinder

Beitrag von gerome69 »

Hallo zusammen,
würde gerne dafür sorgen, daß ein Anwender ein QT-Prog nur einmal unter Linux/Unix ausführen kann.

Unter QT-Windows löse ich das so:

Code: Alles auswählen

#include <windows.h>

[... in main()...]
HANDLE hMutex=CreateMutexA(NULL,TRUE,"ED-NewsEditor");
 bool foundInstance=FALSE;
if (GetLastError()==ERROR_ALREADY_EXISTS) foundInstance=TRUE;
if (hMutex) ReleaseMutex(hMutex);
if (foundInstance) {
    QMessageBox::warning(NULL,"","Programm ist bereits gestartet!"));
    QCoreApplication::exit();
    return 0;
}
Tja, unter Linux/Unix habe ich da erstmal nicht wirklich ne Idee.
Habe mir QMutex und QSemaphore angesehen, aber das geht wohl nur innerhalb der Child-Threads, nicht bei 2 unabhängig gestarteten Anwendungen.

Über Shell-Console-Aufruf ginge es sicher so:
ps ux|grep "appName"|grep -cv "grep" => Anzahl der Starts dieser Anwendung

Finde ich aber nicht wirklich elegant.

Hat jemand ne bessere Idee?

Danke für Tips, Bernd
atlastraeger
Beiträge: 32
Registriert: 11. August 2004 12:42

Beitrag von atlastraeger »

Schau doch mal auf http://www.trolltech.com/products/qt/ad ... plication/.

Vielleicht reicht die spärliche Dokumentation ja für eine eigene Implementierung.
gerome69
Beiträge: 188
Registriert: 28. April 2006 22:50
Wohnort: Berlin
Kontaktdaten:

Beitrag von gerome69 »

atlastraeger hat geschrieben:Schau doch mal auf http://www.trolltech.com/products/qt/ad ... plication/.

Vielleicht reicht die spärliche Dokumentation ja für eine eigene Implementierung.
Ja, sieht sehr gut aus. Genau das bräuchte ich.
Aber auf der Seite gibt es scheinbar keinen Download, nur den Hinweis:
Download Commercial Edition:
Only available for Qt Solutions license holder with a valid Support and Maintenance agreement (authentication required).
Tja, ich habe keine kommerzielle Lizenz. Dann bleibt mir der Zugang verschlossen?!

Gruß, Bernd
ChMaster
Beiträge: 252
Registriert: 23. Februar 2005 14:44
Wohnort: RP -> Alzey
Kontaktdaten:

Beitrag von ChMaster »

genau so wie du es bei windows machst, kannst du es auch unter linux
lösen. schau dir mal QMutex und QMutexLocker an. empfehlenswert währe
auch noch, dir QProcess an zu schauen

das dürfte dir evtl weiter helfen.

ps.:
ist nur ein tip. ich habe QMutex und QMutexLocker noch nicht verwendet :)
ChMaster
------------ Projekte------------
DBoxFE
DMS
First4 (Plugin-Develper)
gerome69
Beiträge: 188
Registriert: 28. April 2006 22:50
Wohnort: Berlin
Kontaktdaten:

Beitrag von gerome69 »

ChMaster hat geschrieben:genau so wie du es bei windows machst, kannst du es auch unter linux
lösen. schau dir mal QMutex und QMutexLocker an. empfehlenswert währe
auch noch, dir QProcess an zu schauen

das dürfte dir evtl weiter helfen.

ps.:
ist nur ein tip. ich habe QMutex und QMutexLocker noch nicht verwendet :)
QMutex hatte ich mir ja schon angeschaut. Bei Windows sind Mutexe systemweit, sogar benutzerübergreifend. Die QMutexe, die ich in der 1. Instanze erzeuge, sind nur für diese Applikation und deren Childs greifbar.
Die als 2. gestartete Appl. kann nicht drauf zugreifen und weiß nicht, daß Appl. 1 schon läuft.
Oder ich hab es grob falsch gemacht?!

Gelöst habe ich es jetzt halt erstmal Shellaufruf:

Code: Alles auswählen

QProcess shell;
shell.start("ps ux");
if (shell.waitForStarted()) { // Falls kein Zugreif auf 'ps' möglich ist, geht der ganze Check nicht :-(
if (shell.waitForFinished()) {
QByteArray result = bash.readAll();
QStringList lines=QString(result).split("\n");
int count=0;
for (int i=0;i<lines.size();++i) 
    if (lines.at(i).indexOf("MyApplication")!=-1) count++;
if (count>1) {QMessageBox::warning(NULL,"","Application already runs.");
Gruß, Bernd
patrik08
Beiträge: 746
Registriert: 27. Februar 2006 10:48
Wohnort: DE Freiburg

Beitrag von patrik08 »

Ich habe es so geloest auf alle OS:

So dass jeder user nur einmal die applikation startet...
und die destrukt class loescht dass file LOCK_FILE_APPLICATION
und alles ist im butter ....

probleme gibt es nur wenn die applikation unstabil ist ... einfriert oder crascht...
dann muuss man per hand dass file loeschen...

Code: Alles auswählen

#define WORK_CACHEDIR \
              QString( "%1/.%2/" ).arg( QDir::homePath() , _PROGRAM_SHORT_NAME )

#define LOCK_FILE_APPLICATION \
              QString( "%1_application.lock" ).arg( WORK_CACHEDIR )

main .......

 QDir dira(WORK_CACHEDIR);
    if ( dira.mkpath(WORK_CACHEDIR) ) { } else {
    QMessageBox::warning( 0, "File error!", "Not possibel to create a work dir on: "+WORK_CACHEDIR);
    return -1;
    } 



if (!db.is_file(LOCK_FILE_APPLICATION)) {
                    db.file_put_contents(LOCK_FILE_APPLICATION,"");
                    Shop_Main::self()->setWindowTitle( _PROGRAM_TITLE );
                    Shop_Main::self()->show();
                    a.connect( &a, SIGNAL( lastWindowClosed() ), &a, SLOT( quit() ) );
                    return a.exec();  
                } else {
                    return -1;
                }
.........................
speack português italiano deutsch english castellà qt
Nassian
Beiträge: 126
Registriert: 20. Juni 2005 21:14

Beitrag von Nassian »

Wenn ich keine Lösung ala Qt-Solutions hätte würde ich einen Socket verwenden. Die Applikation sendet vor dem Start an einen bestimmten Port bestimmte Daten, wenn was zurückkommt läuft schon eine Instanz und tschüss. Besser als die Lösung mit dem File, die wird schon inkonsisten wenn die Applikation absolut stabil läuft.
Emperor_L0ser
Beiträge: 51
Registriert: 28. Juli 2005 12:26
Kontaktdaten:

Beitrag von Emperor_L0ser »

Das mit den Sockets finde ich auch eine schlechte Idee, die Firewall gibt sofort Alarm, was mich als Anwender doch recht stuzig machen würde, wenn ich grade ein Programm starte, das sonst villeicht keine Netzwerkaktivitäten benötigt. Wahrscheinlich würde ich den Netzwerkzugriff blockieren und könnte das Programm damit wieder beliebig oft starten...

Die Version mit den Dateien ist unter Linux bereits ins System eingebaut. Den jeder Prozess bekommt seine eigene pid-Datei
Die beste Möglichkeit ist wohl leider für jedes BS das ganze selber zu bauen, unter Windows mit Mutex und unter Linux mit Dateien. Wobei ich mich frage, was ist es für ein außergewöhnliches Programm, das nur einmal unter Linux gestartet werden soll, warum darf nicht jeder benutzer eins haben?
Antworten