21 #include "kmstartup.h"
24 #include "kcursorsaver.h"
26 #include <tdelocale.h>
27 #include <ksimpleconfig.h>
28 #include <kstandarddirs.h>
29 #include <tdemessagebox.h>
30 #include <dcopclient.h>
32 #include <tdeglobal.h>
33 #include <tdeapplication.h>
34 #include <tdeaboutdata.h>
35 #include <kiconloader.h>
38 #include <sys/types.h>
39 #include <sys/param.h>
51 void kmsignalHandler(
int sigId)
53 kmsetSignalHandler(SIG_DFL);
54 fprintf(stderr,
"*** KMail got signal %d (Exiting)\n", sigId);
56 if (kmkernel) kmkernel->dumpDeadLetters();
61 void kmcrashHandler(
int sigId)
63 kmsetSignalHandler(SIG_DFL);
64 fprintf(stderr,
"*** KMail got signal %d (Crashing)\n", sigId);
66 if (kmkernel) kmkernel->dumpDeadLetters();
72 void kmsetSignalHandler(
void (*handler)(
int))
74 signal(SIGKILL, handler);
75 signal(SIGTERM, handler);
76 signal(SIGHUP, handler);
77 TDECrash::setEmergencySaveFunction(kmcrashHandler);
84 TQString getMyHostName() {
89 if(gethostname(hostNameC, 255))
91 return TQString::fromLocal8Bit(hostNameC);
97 void checkConfigUpdates() {
98 static const char *
const updates[] = {
100 "3.1-update-identities",
101 "3.1-use-identity-uoids",
102 "3.1-new-mail-notification",
103 "3.2-update-loop-on-goto-unread-settings",
104 "3.1.4-dont-use-UOID-0-for-any-identity",
107 "3.3-use-ID-for-accounts",
108 "3.3-update-filter-rules",
109 "3.3-move-identities-to-own-file",
110 "3.3-aegypten-kpgprc-to-kmailrc",
111 "3.3-aegypten-kpgprc-to-libkleopatrarc",
112 "3.3-aegypten-emailidentities-split-sign-encr-keys",
121 "3.5.7-imap-flag-migration"
123 static const int numUpdates =
sizeof updates /
sizeof *updates;
126 TDEConfig * config = KMKernel::config();
127 TDEConfigGroup startup( config,
"Startup" );
128 const int configUpdateLevel = startup.readNumEntry(
"update-level", 0 );
129 if ( configUpdateLevel == numUpdates )
132 for (
int i = configUpdateLevel ; i < numUpdates ; ++i ) {
133 config->checkUpdate( updates[i],
"kmail.upd" );
135 startup.writeEntry(
"update-level", numUpdates );
140 TQString appName = kapp->instanceName();
141 if ( appName.isEmpty() )
144 TQString programName;
145 const TDEAboutData *about = kapp->aboutData();
147 programName = about->programName();
148 if ( programName.isEmpty() )
149 programName = i18n(
"KMail");
151 TQString lockLocation = locateLocal(
"data",
"kmail/lock");
152 KSimpleConfig config(lockLocation);
153 int oldPid = config.readNumEntry(
"pid", -1);
154 const TQString oldHostName = config.readEntry(
"hostname");
155 const TQString oldAppName = config.readEntry(
"appName", appName );
156 const TQString oldProgramName = config.readEntry(
"programName", programName );
157 const TQString hostName = getMyHostName();
158 bool first_instance =
false;
160 first_instance =
true;
161 else if (hostName == oldHostName && oldPid != getpid()) {
164 if ( ::access(
"/proc", X_OK ) == 0 ) {
166 char path_buffer[MAXPATHLEN + 1];
167 path_buffer[MAXPATHLEN] = 0;
168 const TQString procPath = TQString(
"/proc/%1/exe").arg(oldPid);
169 const int length = readlink (procPath.latin1(), path_buffer, MAXPATHLEN);
171 first_instance =
true;
173 path_buffer[length] =
'\0';
174 const TQString path = TQFile::decodeName(path_buffer);
175 kdDebug() << k_funcinfo << path << endl;
176 const int pos = path.findRev(
'/');
177 const TQString fileName = path.mid(pos+1);
178 kdDebug() <<
"Found process " << oldPid <<
" running. It's: " << fileName << endl;
179 first_instance = fileName !=
"kmail" && fileName !=
"kontact";
186 if ( kill(oldPid, 0) == -1 )
187 first_instance = ( errno == ESRCH );
191 if ( !first_instance ) {
193 if ( oldHostName == hostName ) {
197 if ( oldAppName == appName )
198 msg = i18n(
"%1 already seems to be running on another display on "
199 "this machine. Running %2 more than once "
200 "can cause the loss of mail. You should not start %1 "
201 "unless you are sure that it is not already running.")
202 .arg( programName, programName );
208 msg = i18n(
"%1 seems to be running on another display on this "
209 "machine. Running %1 and %2 at the same "
210 "time can cause the loss of mail. You should not start %2 "
211 "unless you are sure that %1 is not running.")
212 .arg( oldProgramName, programName );
215 if ( oldAppName == appName )
216 msg = i18n(
"%1 already seems to be running on %2. Running %1 more "
217 "than once can cause the loss of mail. You should not "
218 "start %1 on this computer unless you are sure that it is "
219 "not already running on %2.")
220 .arg( programName, oldHostName );
222 msg = i18n(
"%1 seems to be running on %3. Running %1 and %2 at the "
223 "same time can cause the loss of mail. You should not "
224 "start %2 on this computer unless you are sure that %1 is "
225 "not running on %3.")
226 .arg( oldProgramName, programName, oldHostName );
230 if ( KMessageBox::No ==
231 KMessageBox::warningYesNo( 0, msg, TQString(),
232 i18n(
"Start %1").arg( programName ),
238 config.writeEntry(
"pid", getpid());
239 config.writeEntry(
"hostname", hostName);
240 config.writeEntry(
"appName", appName );
241 config.writeEntry(
"programName", programName );
245 void insertLibraryCataloguesAndIcons() {
246 static const char *
const catalogues[] = {
253 TDELocale * l = TDEGlobal::locale();
254 TDEIconLoader * il = TDEGlobal::iconLoader();
255 for (
unsigned int i = 0 ; i <
sizeof catalogues /
sizeof *catalogues ; ++i ) {
256 l->insertCatalogue( catalogues[i] );
257 il->addAppDir( catalogues[i] );
264 const TQString lockLocation = locateLocal(
"data",
"kmail/lock");
265 KSimpleConfig config(lockLocation);
266 config.writeEntry(
"pid", -1);
sets a cursor and makes sure it's restored on destruction Create a KCursorSaver object when you want ...