VirtualBox

Changeset 99585 in vbox


Ignore:
Timestamp:
May 3, 2023 3:12:56 PM (19 months ago)
Author:
vboxsync
Message:

Guest Additions/VBoxClient: Implemented "--session-type" parameter and automatic detection of the session type, to detect the current desktop environment at runtime. Makes now use of the VBGHLog facilities. bugref:10427

Location:
trunk/src/VBox/Additions/x11/VBoxClient
Files:
6 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Additions/x11/VBoxClient/Makefile.kmk

    r99565 r99585  
    4848#
    4949PROGRAMS.linux += VBoxDRMClient
     50
     51# Common Guest / Host sources.
     52VBOX_GH_SOURCES := \
     53        $(PATH_ROOT)/src/VBox/GuestHost/Log.cpp \
     54        $(PATH_ROOT)/src/VBox/GuestHost/SessionType.cpp
    5055
    5156VBoxClient_TEMPLATE = VBoxGuestR3Exe
     
    6873        main.cpp \
    6974        logging.cpp
     75VBoxClient_SOURCES += $(VBOX_GH_SOURCES)
    7076
    7177VBoxDRMClient_TEMPLATE = VBoxGuestR3Exe
     
    7985        display-ipc.cpp \
    8086        logging.cpp
    81 
     87VBoxDRMClient_SOURCES += $(VBOX_GH_SOURCES)
    8288
    8389VBoxClient_SOURCES.linux = \
  • trunk/src/VBox/Additions/x11/VBoxClient/VBoxClient.h

    r98474 r99585  
    3737#include <iprt/string.h>
    3838
    39 /** Environment variable which is exported when in Wayland Desktop Environment. */
    40 #define VBCL_ENV_WAYLAND_DISPLAY        "WAYLAND_DISPLAY"
    41 /** Environment variable which contains information about currently running Desktop Environment. */
    42 #define VBCL_ENV_XDG_CURRENT_DESKTOP    "XDG_CURRENT_DESKTOP"
    43 /** Environment variable which contains information about currently running session (X11, Wayland, etc). */
    44 #define VBCL_ENV_XDG_SESSION_TYPE       "XDG_SESSION_TYPE"
     39#include <VBox/GuestHost/Log.h>
     40#include <VBox/GuestHost/SessionType.h>
    4541
    4642int VBClShowNotify(const char *pszHeader, const char *pszBody);
     
    5551void VBClLogDestroy(void);
    5652
    57 /**
    58  * Detect if user is running on Wayland by checking corresponding environment variable.
    59  *
    60  * @returns True if Wayland has been detected, False otherwise.
    61  */
    62 extern bool VBClHasWayland(void);
    63 
    6453/** Call clean-up for the current service and exit. */
    6554extern void VBClShutdown(bool fExit = true);
     55
     56extern VBGHSESSIONTYPE VBClGetSessionType(void);
    6657
    6758/**
  • trunk/src/VBox/Additions/x11/VBoxClient/display-helper-gnome3.cpp

    r98103 r99585  
    964964static DECLCALLBACK(int) vbcl_hlp_gnome3_probe(void)
    965965{
    966     const char *pszCurrentDesktop = RTEnvGet(VBCL_ENV_XDG_CURRENT_DESKTOP);
     966    const char *pszCurrentDesktop = RTEnvGet(VBGH_ENV_XDG_CURRENT_DESKTOP);
    967967
    968968    /* GNOME3 identifies itself by XDG_CURRENT_DESKTOP environment variable.
     
    982982    int rc;
    983983
    984     if (!VBClHasWayland())
     984    if (VBClGetSessionType() == VBGHSESSIONTYPE_X11)
    985985    {
    986986        rc = vbcl_hlp_generic_init();
     
    998998    int rc;
    999999
    1000     if (!VBClHasWayland())
     1000    if (VBClGetSessionType() == VBGHSESSIONTYPE_X11)
    10011001    {
    10021002        rc = vbcl_hlp_generic_term();
  • trunk/src/VBox/Additions/x11/VBoxClient/display-svga-x11.cpp

    r98474 r99585  
    581581    }
    582582
    583     if (VBClHasWayland())
     583    if (VBClGetSessionType() == VBGHSESSIONTYPE_WAYLAND)
    584584    {
    585585        rc = VbglR3DrmClientStart();
  • trunk/src/VBox/Additions/x11/VBoxClient/logging.cpp

    r98103 r99585  
    4040#endif
    4141#include <VBox/VBoxGuestLib.h>
     42
     43#include <VBox/GuestHost/Log.h>
    4244
    4345#include <package-generated.h>
     
    219221}
    220222
    221 
    222 
    223 /**
    224  * Logs a verbose message.
    225  *
    226  * @param   pszFormat   The message text.
    227  * @param   va          Format arguments.
    228  */
    229 static void vbClLogV(const char *pszFormat, va_list va)
    230 {
    231     char *psz = NULL;
    232     RTStrAPrintfV(&psz, pszFormat, va);
    233     AssertPtrReturnVoid(psz);
    234     LogRel(("%s", psz));
    235     RTStrFree(psz);
    236 }
    237 
    238223/**
    239224 * Logs a fatal error, notifies the desktop environment via a message and
     
    245230void VBClLogFatalError(const char *pszFormat, ...)
    246231{
    247     va_list args;
    248     va_start(args, pszFormat);
    249     char *psz = NULL;
    250     RTStrAPrintfV(&psz, pszFormat, args);
    251     va_end(args);
    252 
    253     AssertPtrReturnVoid(psz);
    254     LogFunc(("Fatal Error: %s", psz));
    255     LogRel(("Fatal Error: %s", psz));
    256 
    257     VBClShowNotify("VBoxClient - Fatal Error", psz);
    258 
    259     RTStrFree(psz);
     232    va_list va;
     233    va_start(va, pszFormat);
     234    VBGHLogFatalErrorV(pszFormat, va);
     235    va_end(va);
    260236}
    261237
     
    267243void VBClLogError(const char *pszFormat, ...)
    268244{
    269     va_list args;
    270     va_start(args, pszFormat);
    271     char *psz = NULL;
    272     RTStrAPrintfV(&psz, pszFormat, args);
    273     va_end(args);
    274 
    275     AssertPtrReturnVoid(psz);
    276     LogFunc(("Error: %s", psz));
    277     LogRel(("Error: %s", psz));
    278 
    279     RTStrFree(psz);
     245    va_list va;
     246    va_start(va, pszFormat);
     247    VBGHLogErrorV(pszFormat, va);
     248    va_end(va);
    280249}
    281250
     
    287256void  VBClLogInfo(const char *pszFormat, ...)
    288257{
    289     va_list args;
    290     va_start(args, pszFormat);
    291     vbClLogV(pszFormat, args);
    292     va_end(args);
     258    va_list va;
     259    va_start(va, pszFormat);
     260    VBGHLogInfoV(pszFormat, va);
     261    va_end(va);
    293262}
    294263
     
    303272void VBClLogVerbose(unsigned iLevel, const char *pszFormat, ...)
    304273{
    305     if (iLevel <= g_cVerbosity)
    306     {
    307         va_list va;
    308         va_start(va, pszFormat);
    309         vbClLogV(pszFormat, va);
    310         va_end(va);
    311     }
     274    va_list va;
     275    va_start(va, pszFormat);
     276    VBGHLogVerboseV(iLevel, pszFormat, va);
     277    va_end(va);
    312278}
    313279
  • trunk/src/VBox/Additions/x11/VBoxClient/main.cpp

    r98474 r99585  
    6464#define VBOXCLIENT_OPT_VMSVGA_SESSION       VBOXCLIENT_OPT_SERVICES + 5
    6565#define VBOXCLIENT_OPT_DISPLAY              VBOXCLIENT_OPT_SERVICES + 6
     66#define VBOXCLIENT_OPT_SESSION_TYPE         VBOXCLIENT_OPT_SERVICES + 7
    6667
    6768
     
    9596*********************************************************************************************************************************/
    9697/** The global service state. */
    97 VBCLSERVICESTATE     g_Service = { 0 };
     98VBCLSERVICESTATE       g_Service = { 0 };
    9899
    99100/** Set by the signal handler when being called. */
    100 static volatile bool g_fSignalHandlerCalled = false;
     101static volatile bool   g_fSignalHandlerCalled = false;
    101102/** Critical section for the signal handler. */
    102 static RTCRITSECT    g_csSignalHandler;
     103static RTCRITSECT      g_csSignalHandler;
    103104/** Flag indicating Whether the service starts in daemonized  mode or not. */
    104 bool                 g_fDaemonized = false;
     105bool                   g_fDaemonized = false;
    105106/** The name of our pidfile.  It is global for the benefit of the cleanup
    106107 * routine. */
    107 static char          g_szPidFile[RTPATH_MAX] = "";
     108static char            g_szPidFile[RTPATH_MAX] = "";
    108109/** The file handle of our pidfile.  It is global for the benefit of the
    109110 * cleanup routine. */
    110 static RTFILE        g_hPidFile;
     111static RTFILE          g_hPidFile;
    111112/** The name of pidfile for parent (control) process. */
    112 static char          g_szControlPidFile[RTPATH_MAX] = "";
     113static char            g_szControlPidFile[RTPATH_MAX] = "";
    113114/** The file handle of parent process pidfile. */
    114 static RTFILE        g_hControlPidFile;
     115static RTFILE          g_hControlPidFile;
     116/** The session type to use. */
     117static VBGHSESSIONTYPE g_enmSessionType = VBGHSESSIONTYPE_AUTO;
    115118
    116119/** Global critical section held during the clean-up routine (to prevent it
     
    128131static volatile bool g_fProcessReloadRequested = false;
    129132
    130 /**
    131  * Tries to determine if the session parenting this process is of Xwayland.
    132  * NB: XDG_SESSION_TYPE is a systemd(1) environment variable and is unlikely
    133  * set in non-systemd environments or remote logins.
    134  * Therefore we check the Wayland specific display environment variable first.
    135  */
    136 bool VBClHasWayland(void)
    137 {
    138     const char *const pDisplayType = RTEnvGet(VBCL_ENV_WAYLAND_DISPLAY);
    139     const char *pSessionType;
    140 
    141     if (pDisplayType != NULL)
    142         return true;
    143 
    144     pSessionType = RTEnvGet(VBCL_ENV_XDG_SESSION_TYPE);
    145     if ((pSessionType != NULL) && (RTStrIStartsWith(pSessionType, "wayland")))
    146         return true;
    147 
    148     return false;
    149 }
    150133
    151134/**
     
    182165
    183166/**
     167 * Returns the current session type.
     168 *
     169 * @returns The session type.
     170 */
     171VBGHSESSIONTYPE VBClGetSessionType(void)
     172{
     173    return g_enmSessionType;
     174}
     175
     176/**
    184177 * Xlib error handler for certain errors that we can't avoid.
    185178 */
     
    189182
    190183    XGetErrorText(pDisplay, pError->error_code, errorText, sizeof(errorText));
    191     VBClLogError("An X Window protocol error occurred: %s (error code %d).  Request code: %d, minor code: %d, serial number: %d\n", errorText, pError->error_code, pError->request_code, pError->minor_code, pError->serial);
     184    VBClLogError("An X Window protocol error occurred: %s (error code %d).  Request code: %d, minor code: %d, serial number: %d\n",
     185                 errorText, pError->error_code, pError->request_code, pError->minor_code, pError->serial);
    192186    return 0;
    193187}
     
    332326    RTPrintf("  --display            starts VMSVGA dynamic resizing for legacy guests\n");
    333327#endif
     328    RTPrintf("  --session-type       specifies the session type to use (auto, x11, wayland)\n");
    334329    RTPrintf("  -f, --foreground     run in the foreground (no daemonizing)\n");
    335330    RTPrintf("  -d, --nodaemon       continues running as a system service\n");
     
    506501    bool fUpdateStarted = false;
    507502
    508     /* This should never be called twice in one process - in fact one Display
    509      * object should probably never be used from multiple threads anyway. */
    510     if (!XInitThreads())
    511         return RTMsgErrorExitFailure("Failed to initialize X11 threads\n");
    512 
    513503    /* Get our file name for usage info and hints. */
    514504    const char *pcszFileName = RTPathFilename(argv[0]);
     
    519509    static const RTGETOPTDEF s_aOptions[] =
    520510    {
    521         { "--nodaemon",                     'd',                                      RTGETOPT_REQ_NOTHING },
    522         { "--foreground",                   'f',                                      RTGETOPT_REQ_NOTHING },
    523         { "--help",                         'h',                                      RTGETOPT_REQ_NOTHING },
    524         { "--logfile",                      'l',                                      RTGETOPT_REQ_STRING  },
    525         { "--version",                      'V',                                      RTGETOPT_REQ_NOTHING },
    526         { "--verbose",                      'v',                                      RTGETOPT_REQ_NOTHING },
     511        { "--nodaemon",                     'd',                                RTGETOPT_REQ_NOTHING },
     512        { "--foreground",                   'f',                                RTGETOPT_REQ_NOTHING },
     513        { "--help",                         'h',                                RTGETOPT_REQ_NOTHING },
     514        { "--logfile",                      'l',                                RTGETOPT_REQ_STRING  },
     515        { "--version",                      'V',                                RTGETOPT_REQ_NOTHING },
     516        { "--verbose",                      'v',                                RTGETOPT_REQ_NOTHING },
    527517
    528518        /* Services */
    529519#ifdef VBOX_WITH_GUEST_PROPS
    530         { "--checkhostversion",             VBOXCLIENT_OPT_CHECKHOSTVERSION,          RTGETOPT_REQ_NOTHING },
     520        { "--checkhostversion",             VBOXCLIENT_OPT_CHECKHOSTVERSION,    RTGETOPT_REQ_NOTHING },
    531521#endif
    532522#ifdef VBOX_WITH_SHARED_CLIPBOARD
    533         { "--clipboard",                    VBOXCLIENT_OPT_CLIPBOARD,                 RTGETOPT_REQ_NOTHING },
     523        { "--clipboard",                    VBOXCLIENT_OPT_CLIPBOARD,           RTGETOPT_REQ_NOTHING },
    534524#endif
    535525#ifdef VBOX_WITH_DRAG_AND_DROP
    536         { "--draganddrop",                  VBOXCLIENT_OPT_DRAGANDDROP,               RTGETOPT_REQ_NOTHING },
     526        { "--draganddrop",                  VBOXCLIENT_OPT_DRAGANDDROP,         RTGETOPT_REQ_NOTHING },
    537527#endif
    538528#ifdef VBOX_WITH_SEAMLESS
    539         { "--seamless",                     VBOXCLIENT_OPT_SEAMLESS,                  RTGETOPT_REQ_NOTHING },
     529        { "--seamless",                     VBOXCLIENT_OPT_SEAMLESS,            RTGETOPT_REQ_NOTHING },
    540530#endif
    541531#ifdef VBOX_WITH_VMSVGA
    542         { "--vmsvga",                       VBOXCLIENT_OPT_VMSVGA,                    RTGETOPT_REQ_NOTHING },
    543         { "--vmsvga-session",               VBOXCLIENT_OPT_VMSVGA_SESSION,            RTGETOPT_REQ_NOTHING },
    544         { "--display",                      VBOXCLIENT_OPT_DISPLAY,                    RTGETOPT_REQ_NOTHING },
    545 #endif
     532        { "--vmsvga",                       VBOXCLIENT_OPT_VMSVGA,              RTGETOPT_REQ_NOTHING },
     533        { "--vmsvga-session",               VBOXCLIENT_OPT_VMSVGA_SESSION,      RTGETOPT_REQ_NOTHING },
     534        { "--display",                      VBOXCLIENT_OPT_DISPLAY,             RTGETOPT_REQ_NOTHING },
     535#endif
     536        { "--session-type",                 VBOXCLIENT_OPT_SESSION_TYPE,        RTGETOPT_REQ_STRING }
    546537    };
    547538
     
    674665            }
    675666#endif
     667            case VBOXCLIENT_OPT_SESSION_TYPE:
     668            {
     669                if (!RTStrICmp(ValueUnion.psz, "x11"))
     670                    g_enmSessionType = VBGHSESSIONTYPE_X11;
     671                else if (!RTStrICmp(ValueUnion.psz, "wayland"))
     672                    g_enmSessionType = VBGHSESSIONTYPE_WAYLAND;
     673                else if (!RTStrICmp(ValueUnion.psz, "none"))
     674                    g_enmSessionType = VBGHSESSIONTYPE_NONE;
     675                else if (!RTStrICmp(ValueUnion.psz, "auto"))
     676                    g_enmSessionType = VBGHSESSIONTYPE_AUTO;
     677                else
     678                {
     679                    RTMsgError("Session type \"%s\" is invalid; defaulting to \"auto\" instead.\n", ValueUnion.psz);
     680                    g_enmSessionType = VBGHSESSIONTYPE_AUTO;
     681                }
     682                break;
     683            }
     684
    676685            case VINF_GETOPT_NOT_OPTION:
    677686                break;
     
    726735    }
    727736
    728     VBClLogInfo("VBoxClient %s r%s started. Verbose level = %d. Wayland environment detected: %s\n",
    729                 RTBldCfgVersion(), RTBldCfgRevisionStr(), g_cVerbosity, VBClHasWayland() ? "yes" : "no");
     737    VBClLogInfo("VBoxClient %s r%s started. Verbose level = %d\n",
     738                RTBldCfgVersion(), RTBldCfgRevisionStr(), g_cVerbosity);
     739
     740    /* Try to detect the current session type early on, if needed. */
     741    if (g_enmSessionType == VBGHSESSIONTYPE_AUTO)
     742    {
     743        g_enmSessionType = VBGHSessionTypeDetect();
     744    }
     745    else
     746        VBClLogInfo("Session type was manually set to: %s\n", VBGHSessionTypeToStr(g_enmSessionType));
     747
     748    VBClLogInfo("Session type is: %s\n", VBGHSessionTypeToStr(g_enmSessionType));
     749
    730750    VBClLogInfo("Service: %s\n", g_Service.pDesc->pszDesc);
    731751
     
    774794    }
    775795
    776 #ifndef VBOXCLIENT_WITHOUT_X11
    777     /* Set an X11 error handler, so that we don't die when we get unavoidable
    778      * errors. */
    779     XSetErrorHandler(vboxClientXLibErrorHandler);
    780     /* Set an X11 I/O error handler, so that we can shutdown properly on
    781      * fatal errors. */
    782     XSetIOErrorHandler(vboxClientXLibIOErrorHandler);
    783 #endif
     796    if (g_enmSessionType == VBGHSESSIONTYPE_X11)
     797    {
     798        /* This should never be called twice in one process - in fact one Display
     799         * object should probably never be used from multiple threads anyway. */
     800        if (!XInitThreads())
     801            return RTMsgErrorExitFailure("Failed to initialize X11 threads\n");
     802        /* Set an X11 error handler, so that we don't die when we get unavoidable
     803         * errors. */
     804        XSetErrorHandler(vboxClientXLibErrorHandler);
     805        /* Set an X11 I/O error handler, so that we can shutdown properly on
     806         * fatal errors. */
     807        XSetIOErrorHandler(vboxClientXLibIOErrorHandler);
     808    }
    784809
    785810    bool fSignalHandlerInstalled = false;
Note: See TracChangeset for help on using the changeset viewer.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette