Skip to content

Commit

Permalink
A somewhat hackish way of making kdeinit work in su sessions, but I c…
Browse files Browse the repository at this point in the history
…ouldn't

think of anything better. Kdeinit should still clean up properly in such
sessions and exit after a timeout, like dcopserver did in KDE3.
BUG: 75492


svn path=/trunk/KDE/kdelibs/; revision=1132903
  • Loading branch information
llunak committed May 31, 2010
1 parent 04194e0 commit 6891c6f
Showing 1 changed file with 37 additions and 0 deletions.
37 changes: 37 additions & 0 deletions kinit/kinit.cpp
Expand Up @@ -64,6 +64,7 @@
#include <klocale.h>
#include <kdebug.h>
#include <kde_file.h>
#include <ksavefile.h>

#ifdef Q_OS_LINUX
#include <sys/prctl.h>
Expand Down Expand Up @@ -1574,6 +1575,42 @@ static void setupX()
{
XSetIOErrorHandler(kdeinit_xio_errhandler);
XSetErrorHandler(kdeinit_x_errhandler);
/*
Handle the tricky case of running via kdesu/su/sudo/etc. There the usual case
is that kdesu (etc.) creates a file with xauth information, sets XAUTHORITY,
runs the command and removes the xauth file after the command finishes. However,
dbus and kdeinit daemon currently don't clean up properly and keeping running.
Which means that running a KDE app via kdesu the second time talks to kdeinit
with obsolete xauth information, which makes it unable to connect to X or launch
any X11 applications.
Even fixing the cleanup probably wouldn't be sufficient, since it'd be possible to
launch one kdesu session, another one, exit the first one and the app from the second
session would be using kdeinit from the first one.
So the trick here is to duplicate the xauth file to another file in KDE's tmp
location, make the file have a consistent name so that future sessions will use it
as well, point XAUTHORITY there and never remove the file (except for possible
tmp cleanup).
*/
if( !qgetenv( "XAUTHORITY" ).isEmpty()) {
QByteArray display = qgetenv( DISPLAY );
int i;
if((i = display.lastIndexOf('.')) > display.lastIndexOf(':') && i >= 0)
display.truncate(i);
display.replace(':','_');
#ifdef __APPLE__
display.replace('/','_');
#endif
QString xauth = s_instance->dirs()->saveLocation( "tmp" ) + QLatin1String( "xauth-" )
+ QString::number( getuid()) + QLatin1String( "-" ) + QString::fromLocal8Bit( display );
KSaveFile xauthfile( xauth );
QFile xauthfrom( QFile::decodeName( qgetenv( "XAUTHORITY" )));
if( !xauthfrom.open( QFile::ReadOnly ) || !xauthfile.open( QFile::WriteOnly )
|| xauthfile.write( xauthfrom.readAll()) != xauthfrom.size() || !xauthfile.finalize()) {
xauthfile.abort();
} else {
setenv( "XAUTHORITY", QFile::encodeName( xauth ), true );
}
}
}

// Borrowed from kdebase/kaudio/kaudioserver.cpp
Expand Down

0 comments on commit 6891c6f

Please sign in to comment.