/* * Main program */ int main(int argc, char *argv[]) { char *p; char errormsg[256]; static char environment_name[] = "SESSION_MANAGER"; int success, found_command_line_name, i; Argc = argc; Argv = argv; for (i = 1; i < argc; i++) { if (argv[i][0] == '-') { switch (argv[i][1]) { case 'd': /* -display */ if (++i >= argc) goto usage; cmd_line_display = (char *) XtNewString (argv[i]); continue; case 's': /* -session */ if (++i >= argc) goto usage; session_name = XtNewString (argv[i]); continue; case 'v': /* -verbose */ verbose = 1; continue; } } usage: fprintf (stderr, "usage: xsm [-display display] [-session session_name] [-verbose]\n"); exit (1); } topLevel = XtVaAppInitialize (&appContext, "XSm", NULL, 0, &argc, argv, NULL, XtNmappedWhenManaged, False, XtNwindowRole, "xsm main window", NULL); wmStateAtom = XInternAtom ( XtDisplay (topLevel), "WM_STATE", False); wmDeleteAtom = XInternAtom ( XtDisplay (topLevel), "WM_DELETE_WINDOW", False); register_signals (appContext); /* * Install an IO error handler. For an explanation, * see the comments for InstallIOErrorHandler(). */ InstallIOErrorHandler (); /* * Init SM lib */ if (!SmsInitialize ("SAMPLE-SM", "1.0", NewClientProc, NULL, HostBasedAuthProc, 256, errormsg)) { fprintf (stderr, "%s\n", errormsg); exit (1); } if (!IceListenForConnections (&numTransports, &listenObjs, 256, errormsg)) { fprintf (stderr, "%s\n", errormsg); exit (1); } atexit(CloseListeners); if (!SetAuthentication (numTransports, listenObjs, &authDataEntries)) { fprintf (stderr, "Could not set authorization\n"); exit (1); } InitWatchProcs (appContext); for (i = 0; i < numTransports; i++) { XtAppAddInput (appContext, IceGetListenConnectionNumber (listenObjs[i]), (XtPointer) XtInputReadMask, NewConnectionXtProc, (XtPointer) listenObjs[i]); } /* the sizeof includes the \0, so we don't need to count the '=' */ networkIds = IceComposeNetworkIdList (numTransports, listenObjs); p = (char *) XtMalloc((sizeof environment_name) + strlen(networkIds) + 1); if(!p) nomem(); sprintf(p, "%s=%s", environment_name, networkIds); putenv(p); if (cmd_line_display) { /* * If a display was passed on the command line, set the DISPLAY * environment in this process so all applications started by * the session manager will run on the specified display. */ p = (char *) XtMalloc(8 + strlen(cmd_line_display) + 1); sprintf(p, "DISPLAY=%s", cmd_line_display); putenv(p); } if (verbose) printf ("setenv %s %s\n", environment_name, networkIds); create_choose_session_popup (); create_main_window (); create_client_info_popup (); create_save_popup (); create_log_popup (); /* * Initalize all lists */ RunningList = ListInit(); if(!RunningList) nomem(); PendingList = ListInit(); if(!PendingList) nomem(); RestartAnywayList = ListInit(); if(!RestartAnywayList) nomem(); RestartImmedList = ListInit(); if(!RestartImmedList) nomem(); WaitForSaveDoneList = ListInit(); if (!WaitForSaveDoneList) nomem(); InitialSaveList = ListInit(); if (!InitialSaveList) nomem(); FailedSaveList = ListInit(); if (!FailedSaveList) nomem(); WaitForInteractList = ListInit(); if (!WaitForInteractList) nomem(); WaitForPhase2List = ListInit(); if (!WaitForPhase2List) nomem(); /* * Get list of session names. If a session name was found on the * command line, and it is in the list of session names we got, then * use that session name. If there were no session names found, then * use the default session name. Otherwise, present a list of session * names for the user to choose from. */ success = GetSessionNames (&sessionNameCount, &sessionNamesShort, &sessionNamesLong, &sessionsLocked); found_command_line_name = 0; if (success && session_name) { for (i = 0; i < sessionNameCount; i++) if (strcmp (session_name, sessionNamesShort[i]) == 0) { found_command_line_name = 1; if (sessionsLocked[i]) { fprintf (stderr, "Session '%s' is locked\n", session_name); exit (1); } break; } } if (!success || found_command_line_name) { FreeSessionNames (sessionNameCount, sessionNamesShort, sessionNamesLong, sessionsLocked); if (!found_command_line_name) session_name = XtNewString (DEFAULT_SESSION_NAME); if (!StartSession (session_name, !found_command_line_name)) UnableToLockSession (session_name); } else { ChooseSession (); } /* * Main loop */ XtAppMainLoop (appContext); exit(0); }
KSMServer::KSMServer( const QString& windowManager, bool _only_local, bool lockscreen ) : wmProcess( NULL ) , sessionGroup( "" ) , logoutEffectWidget( NULL ) { #ifdef COMPILE_SCREEN_LOCKER KGlobal::locale()->insertCatalog(QLatin1String( "libkworkspace" )); ScreenLocker::KSldApp::self(); if (lockscreen) { ScreenLocker::KSldApp::self()->lock(); } #else Q_UNUSED(lockscreen) #endif new KSMServerInterfaceAdaptor( this ); QDBusConnection::sessionBus().registerObject("/KSMServer", this); klauncherSignals = new OrgKdeKLauncherInterface(QLatin1String("org.kde.klauncher"), QLatin1String("/KLauncher"), QDBusConnection::sessionBus()); kcminitSignals = NULL; the_server = this; clean = false; shutdownType = KWorkSpace::ShutdownTypeNone; state = Idle; dialogActive = false; saveSession = false; wmPhase1WaitingCount = 0; KConfigGroup config(KGlobal::config(), "General"); clientInteracting = 0; xonCommand = config.readEntry( "xonCommand", "xon" ); KGlobal::dirs()->addResourceType( "windowmanagers", "data", "ksmserver/windowmanagers" ); selectWm( windowManager ); connect( &startupSuspendTimeoutTimer, SIGNAL(timeout()), SLOT(startupSuspendTimeout())); connect( &pendingShutdown, SIGNAL(timeout()), SLOT(pendingShutdownTimeout())); only_local = _only_local; #ifdef HAVE__ICETRANSNOLISTEN if (only_local) _IceTransNoListen("tcp"); #else only_local = false; #endif char errormsg[256]; if (!SmsInitialize ( (char*) KSMVendorString, (char*) KSMReleaseString, KSMNewClientProc, (SmPointer) this, HostBasedAuthProc, 256, errormsg ) ) { qWarning("KSMServer: could not register XSM protocol"); } if (!IceListenForConnections (&numTransports, &listenObjs, 256, errormsg)) { qWarning("KSMServer: Error listening for connections: %s", errormsg); qWarning("KSMServer: Aborting."); exit(1); } { // publish available transports. QByteArray fName = QFile::encodeName(KStandardDirs::locateLocal("socket", "KSMserver")); QString display = ::getenv("DISPLAY"); // strip the screen number from the display display.replace(QRegExp("\\.[0-9]+$"), ""); int i; while( (i = display.indexOf(':')) >= 0) display[i] = '_'; while( (i = display.indexOf('/')) >= 0) display[i] = '_'; fName += '_'+display.toLocal8Bit(); FILE *f; f = ::fopen(fName.data(), "w+"); if (!f) { qWarning("KSMServer: cannot open %s: %s", fName.data(), strerror(errno)); qWarning("KSMServer: Aborting."); exit(1); } char* session_manager = IceComposeNetworkIdList(numTransports, listenObjs); fprintf(f, "%s\n%i\n", session_manager, getpid()); fclose(f); setenv( "SESSION_MANAGER", session_manager, true ); // Pass env. var to kdeinit. org::kde::KLauncher klauncher("org.kde.klauncher", "/KLauncher", QDBusConnection::sessionBus()); klauncher.setLaunchEnv( "SESSION_MANAGER", (const char*) session_manager ); free(session_manager); } if (only_local) { if (!SetAuthentication_local(numTransports, listenObjs)) qFatal("KSMSERVER: authentication setup failed."); } else { if (!SetAuthentication(numTransports, listenObjs, &authDataEntries)) qFatal("KSMSERVER: authentication setup failed."); } IceAddConnectionWatch (KSMWatchProc, (IcePointer) this); KSMListener* con; for ( int i = 0; i < numTransports; i++) { fcntl( IceGetListenConnectionNumber( listenObjs[i] ), F_SETFD, FD_CLOEXEC ); con = new KSMListener( listenObjs[i] ); listener.append( con ); connect( con, SIGNAL(activated(int)), this, SLOT(newConnection(int)) ); } signal(SIGHUP, sighandler); signal(SIGTERM, sighandler); signal(SIGINT, sighandler); signal(SIGPIPE, SIG_IGN); connect( &protectionTimer, SIGNAL(timeout()), this, SLOT(protectionTimeout()) ); connect( &restoreTimer, SIGNAL(timeout()), this, SLOT(tryRestoreNext()) ); connect( qApp, SIGNAL(aboutToQuit()), this, SLOT(cleanUp()) ); }
int doSetupPMListen( char * pm_port, int * size_pm_listen_array, int ** pm_listen_array, IceListenObj ** listen_objects, int * nfds, fd_set * rinit) { int num_fds_returned; char errormsg[256]; int fd_counter; IceListenObj * temp_obj; /* * establish PM listeners */ if (!IceListenForWellKnownConnections(pm_port, &num_fds_returned, listen_objects, 256, errormsg)) { (void) fprintf(stderr, "IceListenForWellKnowConnections error: %s\n", errormsg); return 0; } /* * Create space for pm_listen_array */ *pm_listen_array = (int *) malloc (num_fds_returned * sizeof (int *)); if (!pm_listen_array) { (void) fprintf (stderr, "malloc - pm_listen_array\n"); return 0; } *size_pm_listen_array = num_fds_returned; /* * obtain the PM listen fd's for the connection objects */ for (fd_counter = 0; fd_counter < num_fds_returned; fd_counter++) { /* * get fd(s) for PM listen (could be more than one if different * transport mechanisms) */ temp_obj = *listen_objects; IceSetHostBasedAuthProc(temp_obj[fd_counter], FWPHostBasedAuthProc); (*pm_listen_array)[fd_counter] = IceGetListenConnectionNumber(temp_obj[fd_counter]); /* * set all read mask bits on which we are going to select(); * [NOTE: We don't care about write bits here because we don't * use select() to manage writing to the PM] */ FD_SET((*pm_listen_array)[fd_counter], rinit); /* * compute nfds for select() */ *nfds = max(*nfds, (*pm_listen_array)[fd_counter] + 1); } return 1; }
KSMListener( IceListenObj obj ) : QSocketNotifier( IceGetListenConnectionNumber( obj ), QSocketNotifier::Read ) { listenObj = obj; }
gboolean ice_setup_listeners (int num_listeners, IceListenObj *listen_objs, XfsmManager *manager) { GIOChannel *channel; char *auth_setup_file; gchar *command; FILE *cleanup_fp; FILE *setup_fp; int fd; int n; IceSetIOErrorHandler (ice_error_handler); IceAddConnectionWatch (ice_connection_watch, manager); cleanup_fp = ice_tmpfile(&auth_cleanup_file); if (cleanup_fp == NULL) return FALSE; setup_fp = ice_tmpfile(&auth_setup_file); if (setup_fp == NULL) { fclose (cleanup_fp); unlink (auth_cleanup_file); g_free (auth_cleanup_file); return FALSE; } for (n = 0; n < num_listeners; n++) { fd = IceGetListenConnectionNumber (listen_objs[n]); /* Make sure we don't pass on these file descriptors to an * exec'd child process. */ fcntl (fd, F_SETFD, fcntl (fd, F_GETFD, 0) | FD_CLOEXEC); channel = g_io_channel_unix_new (fd); g_io_add_watch (channel, G_IO_ERR | G_IO_HUP | G_IO_IN, ice_connection_accept, listen_objs[n]); g_io_channel_unref (channel); /* setup auth for this listener */ ice_auth_add (setup_fp, cleanup_fp, "ICE", listen_objs[n]); ice_auth_add (setup_fp, cleanup_fp, "XSMP", listen_objs[n]); IceSetHostBasedAuthProc (listen_objs[n], ice_auth_proc); } fclose (setup_fp); fclose (cleanup_fp); /* setup ICE authority and remove setup file */ command = g_strdup_printf ("%s source %s", ICEAUTH_CMD, auth_setup_file); if (system (command) != 0) { g_warning ("Failed to setup the ICE authentication data, session " "management might not work properly."); } g_free (command); unlink (auth_setup_file); g_free (auth_setup_file); return TRUE; }