VirtualBox

Ignore:
Timestamp:
Oct 31, 2013 4:40:46 PM (11 years ago)
Author:
vboxsync
Message:

Guest Control:

  • Implemented IGuestSession::DirectoryRemove, IGuestSession::DirectoryRemoveRecursive, IGuestSession::DirectoryRename + IGuestSession::FileRename.
  • Added appropriate commands to VBoxManage (basic support for now).
  • Implemented support for proper guest session process termination via SCM.
  • Implemented support for internal anonymous wait events which are not relying on the public API's VBoxEventType_T.
  • Various bugfixes.
Location:
trunk/src/VBox/Additions/common/VBoxService
Files:
4 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Additions/common/VBoxService/VBoxService.cpp

    r46506 r49349  
    216216/**
    217217 * Creates the default release logger outputting to the specified file.
     218 * Pass NULL for disabled logging.
    218219 *
    219220 * @return  IPRT status code.
     
    222223int VBoxServiceLogCreate(const char *pszLogFile)
    223224{
     225    if (!pszLogFile) /* No logging wanted? Take a shortcut. */
     226        return VINF_SUCCESS;
     227
    224228    /* Create release logger (stdout + file). */
    225229    static const char * const s_apszGroups[] = VBOX_LOGGROUP_NAMES;
  • trunk/src/VBox/Additions/common/VBoxService/VBoxServiceControl.cpp

    r47817 r49349  
    268268                     * The global session object then acts as a host for all
    269269                     * started guest processes which bring all their
    270                      * credentials with them with the actual execution call.
     270                     * credentials with them with the actual guest process
     271                     * execution call.
    271272                     */
    272273                    if (ctxHost.uProtocol == 1)
     
    407408
    408409    /*
    409      * Ask the host service to cancel all pending requests so that we can
    410      * shutdown properly here.
     410     * Ask the host service to cancel all pending requests for the main
     411     * control thread so that we can shutdown properly here.
    411412     */
    412413    if (g_uControlSvcClientID)
  • trunk/src/VBox/Additions/common/VBoxService/VBoxServiceControlProcess.cpp

    r47695 r49349  
    525525                                     pProcess->uPID, PROC_STS_STARTED, 0 /* u32Flags */,
    526526                                     NULL /* pvData */, 0 /* cbData */);
     527    if (RT_FAILURE(rc))
     528        VBoxServiceError("[PID %RU32]: Error reporting starting status to host, rc=%Rrc\n",
     529                         pProcess->uPID, rc);
    527530
    528531    /*
     
    576579                        if (RT_FAILURE(rc2))
    577580                            VBoxServiceError("Draining IPC notification pipe failed with rc=%Rrc\n", rc2);
    578 #ifdef DEBUG
     581
     582                        /* Process all pending requests. */
    579583                        VBoxServiceVerbose(4, "[PID %RU32]: Processing pending requests ...\n",
    580584                                           pProcess->uPID);
    581 #endif
    582                         /* Process all pending requests. */
    583585                        Assert(pProcess->hReqQueue != NIL_RTREQQUEUE);
    584586                        rc2 = RTReqQueueProcess(pProcess->hReqQueue,
  • trunk/src/VBox/Additions/common/VBoxService/VBoxServiceControlSession.cpp

    r49039 r49349  
    2323#include <iprt/asm.h>
    2424#include <iprt/assert.h>
     25#include <iprt/dir.h>
    2526#include <iprt/env.h>
    2627#include <iprt/file.h>
     
    5758static DECLCALLBACK(int)    gstcntlSessionThread(RTTHREAD ThreadSelf, void *pvUser);
    5859/* Host -> Guest handlers. */
     60static int                  gstcntlSessionHandleDirRemove(PVBOXSERVICECTRLSESSION pSession, PVBGLR3GUESTCTRLCMDCTX pHostCtx);
    5961static int                  gstcntlSessionHandleFileOpen(PVBOXSERVICECTRLSESSION pSession, PVBGLR3GUESTCTRLCMDCTX pHostCtx);
    6062static int                  gstcntlSessionHandleFileClose(const PVBOXSERVICECTRLSESSION pSession, PVBGLR3GUESTCTRLCMDCTX pHostCtx);
     
    6365static int                  gstcntlSessionHandleFileSeek(const PVBOXSERVICECTRLSESSION pSession, PVBGLR3GUESTCTRLCMDCTX pHostCtx);
    6466static int                  gstcntlSessionHandleFileTell(const PVBOXSERVICECTRLSESSION pSession, PVBGLR3GUESTCTRLCMDCTX pHostCtx);
     67static int                  gstcntlSessionHandlePathRename(const PVBOXSERVICECTRLSESSION pSession, PVBGLR3GUESTCTRLCMDCTX pHostCtx);
    6568static int                  gstcntlSessionHandleProcExec(const PVBOXSERVICECTRLSESSION pSession, PVBGLR3GUESTCTRLCMDCTX pHostCtx);
    6669static int                  gstcntlSessionHandleProcInput(const PVBOXSERVICECTRLSESSION pSession, PVBGLR3GUESTCTRLCMDCTX pHostCtx, void *pvScratchBuf, size_t cbScratchBuf);
     
    118121
    119122    return NULL;
     123}
     124
     125
     126static int gstcntlSessionHandleDirRemove(PVBOXSERVICECTRLSESSION pSession,
     127                                         PVBGLR3GUESTCTRLCMDCTX pHostCtx)
     128{
     129    AssertPtrReturn(pSession, VERR_INVALID_POINTER);
     130    AssertPtrReturn(pHostCtx, VERR_INVALID_POINTER);
     131
     132    char szDir[RTPATH_MAX];
     133    uint32_t uFlags = 0;
     134
     135    int rc = VbglR3GuestCtrlDirGetRemove(pHostCtx,
     136                                         /* Directory to remove. */
     137                                         szDir, sizeof(szDir),
     138                                         /* Flags of type DIRREMOVE_FLAG_. */
     139                                         &uFlags);
     140    if (RT_SUCCESS(rc))
     141    {
     142        uint32_t uFlagsRemRec = 0;
     143        bool fRecursive = false;
     144
     145        if (!(uFlags & ~DIRREMOVE_FLAG_VALID_MASK))
     146        {
     147            if (uFlags & DIRREMOVE_FLAG_RECURSIVE)
     148            {
     149                /* Note: DIRREMOVE_FLAG_RECURSIVE must be set explicitly.
     150                 *       Play safe here. */
     151                fRecursive = true;
     152            }
     153
     154            if (uFlags & DIRREMOVE_FLAG_CONTENT_AND_DIR)
     155            {
     156                /* Setting direct value is intentional. */
     157                uFlagsRemRec = RTDIRRMREC_F_CONTENT_AND_DIR;
     158            }
     159
     160            if (uFlags & DIRREMOVE_FLAG_CONTENT_ONLY)
     161            {
     162                /* Setting direct value is intentional. */
     163                uFlagsRemRec |= RTDIRRMREC_F_CONTENT_ONLY;
     164            }
     165        }
     166        else
     167            rc = VERR_NOT_SUPPORTED;
     168
     169        VBoxServiceVerbose(4, "[Dir %s]: Removing with uFlags=0x%x, fRecursive=%RTbool\n",
     170                           szDir, uFlags, fRecursive);
     171
     172        if (RT_SUCCESS(rc))
     173        {
     174            /** @todo Add own recursive function (or a new IPRT function w/ callback?) to
     175             *        provide guest-to-host progress reporting. */
     176            if (fRecursive)
     177                rc = RTDirRemoveRecursive(szDir, uFlagsRemRec);
     178            else
     179                rc = RTDirRemove(szDir);
     180        }
     181
     182        /* Report back in any case. */
     183        int rc2 = VbglR3GuestCtrlMsgReply(pHostCtx, rc);
     184        if (RT_FAILURE(rc2))
     185            VBoxServiceError("[Dir %s]: Failed to report removing status, rc=%Rrc\n",
     186                             szDir, rc2);
     187        if (RT_SUCCESS(rc))
     188            rc = rc2;
     189    }
     190
     191#ifdef DEBUG
     192    VBoxServiceVerbose(4, "Removing directory \"%s\" returned rc=%Rrc\n",
     193                       szDir, rc);
     194#endif
     195    return rc;
    120196}
    121197
     
    583659    VBoxServiceVerbose(4, "Telling file \"%s\" (handle=%RU32) returned rc=%Rrc\n",
    584660                       pFile ? pFile->szName : "<Not found>", uHandle, rc);
     661#endif
     662    return rc;
     663}
     664
     665
     666static int gstcntlSessionHandlePathRename(PVBOXSERVICECTRLSESSION pSession,
     667                                          PVBGLR3GUESTCTRLCMDCTX pHostCtx)
     668{
     669    AssertPtrReturn(pSession, VERR_INVALID_POINTER);
     670    AssertPtrReturn(pHostCtx, VERR_INVALID_POINTER);
     671
     672    char szSource[RTPATH_MAX];
     673    char szDest[RTPATH_MAX];
     674    uint32_t uFlags = 0;
     675
     676    int rc = VbglR3GuestCtrlPathGetRename(pHostCtx,
     677                                          szSource, sizeof(szSource),
     678                                          szDest, sizeof(szDest),
     679                                          /* Flags of type PATHRENAME_FLAG_. */
     680                                          &uFlags);
     681    if (RT_SUCCESS(rc))
     682    {
     683        if (uFlags & ~PATHRENAME_FLAG_VALID_MASK)
     684            rc = VERR_NOT_SUPPORTED;
     685
     686        VBoxServiceVerbose(4, "Renaming \"%s\" to \"%s\", uFlags=0x%x, rc=%Rrc\n",
     687                           szSource, szDest, uFlags, rc);
     688
     689        if (RT_SUCCESS(rc))
     690        {
     691            if (uFlags & PATHRENAME_FLAG_NO_REPLACE)
     692                uFlags |= RTPATHRENAME_FLAGS_NO_REPLACE;
     693
     694            if (uFlags & PATHRENAME_FLAG_REPLACE)
     695                uFlags |= RTPATHRENAME_FLAGS_REPLACE;
     696
     697            if (uFlags & PATHRENAME_FLAG_NO_SYMLINKS)
     698                uFlags |= RTPATHRENAME_FLAGS_NO_SYMLINKS;
     699
     700            rc = RTPathRename(szSource, szDest, uFlags);
     701        }
     702
     703        /* Report back in any case. */
     704        int rc2 = VbglR3GuestCtrlMsgReply(pHostCtx, rc);
     705        if (RT_FAILURE(rc2))
     706            VBoxServiceError("Failed to report renaming status, rc=%Rrc\n", rc2);
     707        if (RT_SUCCESS(rc))
     708            rc = rc2;
     709    }
     710
     711#ifdef DEBUG
     712    VBoxServiceVerbose(4, "Renaming \"%s\" to \"%s\" returned rc=%Rrc\n",
     713                       szSource, szDest, rc);
    585714#endif
    586715    return rc;
     
    9051034    switch (uMsg)
    9061035    {
    907         case HOST_CANCEL_PENDING_WAITS:
    908             VBoxServiceVerbose(1, "We were asked to quit ...\n");
    909             /* Fall thru is intentional. */
    9101036        case HOST_SESSION_CLOSE:
    911             /* Shutdown this fork. */
     1037            /* Shutdown (this fork). */
    9121038            rc = GstCntlSessionClose(pSession);
    9131039            *pfShutdown = true; /* Shutdown in any case. */
     1040            break;
     1041
     1042        case HOST_DIR_REMOVE:
     1043            rc = fImpersonated
     1044               ? gstcntlSessionHandleDirRemove(pSession, pHostCtx)
     1045               : VERR_NOT_SUPPORTED;
    9141046            break;
    9151047
     
    9841116            rc = fImpersonated
    9851117               ? gstcntlSessionHandleFileTell(pSession, pHostCtx)
     1118               : VERR_NOT_SUPPORTED;
     1119            break;
     1120
     1121        case HOST_PATH_RENAME:
     1122            rc = fImpersonated
     1123               ? gstcntlSessionHandlePathRename(pSession, pHostCtx)
    9861124               : VERR_NOT_SUPPORTED;
    9871125            break;
     
    10571195    if (RT_SUCCESS(rc))
    10581196    {
    1059         uint32_t uTimeoutsMS = 5 * 60 * 1000; /** @todo Make this configurable. Later. */
     1197        uint32_t uTimeoutsMS = 30 * 1000; /** @todo Make this configurable. Later. */
    10601198        uint64_t u64TimeoutStart = 0;
    10611199
     
    10801218                if (!u64TimeoutStart)
    10811219                {
    1082                     VBoxServiceVerbose(3, "Guest session ID=%RU32 thread was asked to terminate, waiting for session process to exit ...\n",
    1083                                        uSessionID);
     1220                    VBoxServiceVerbose(3, "Notifying guest session process (PID=%RU32, session ID=%RU32) ...\n",
     1221                                       pThread->hProcess, uSessionID);
     1222
     1223                    VBGLR3GUESTCTRLCMDCTX hostCtx = { uClientID,
     1224                                                      VBOX_GUESTCTRL_CONTEXTID_MAKE_SESSION(uSessionID),
     1225                                                      pThread->StartupInfo.uProtocol, 2 /* uNumParms */ };
     1226                    rc = VbglR3GuestCtrlSessionClose(&hostCtx, 0 /* uFlags */);
     1227                    if (RT_FAILURE(rc))
     1228                    {
     1229                        VBoxServiceError("Unable to notify guest session process (PID=%RU32, session ID=%RU32), rc=%Rrc\n",
     1230                                         pThread->hProcess, uSessionID, rc);
     1231
     1232                        if (rc == VERR_NOT_SUPPORTED)
     1233                        {
     1234                            /* Terminate guest session process in case it's not supported by a too old host. */
     1235                            rc = RTProcTerminate(pThread->hProcess);
     1236                            VBoxServiceVerbose(3, "Terminating guest session process (PID=%RU32) ended with rc=%Rrc\n",
     1237                                               pThread->hProcess, rc);
     1238                        }
     1239                        break;
     1240                    }
     1241
     1242                    VBoxServiceVerbose(3, "Guest session ID=%RU32 thread was asked to terminate, waiting for session process to exit (%RU32ms timeout) ...\n",
     1243                                       uSessionID, uTimeoutsMS);
    10841244                    u64TimeoutStart = RTTimeMilliTS();
     1245
    10851246                    continue; /* Don't waste time on waiting. */
    10861247                }
     
    12221383                                           GUEST_SESSION_NOTIFYTYPE_STARTED, VINF_SUCCESS);
    12231384    if (RT_FAILURE(rc2))
     1385    {
    12241386        VBoxServiceError("Reporting session ID=%RU32 started status failed with rc=%Rrc\n",
    12251387                         pSession->StartupInfo.uSessionID, rc2);
     1388
     1389        /*
     1390         * If session status cannot be posted to the host for
     1391         * some reason, bail out.
     1392         */
     1393        if (RT_SUCCESS(rc))
     1394            rc = rc2;
     1395    }
    12261396
    12271397    /* Allocate a scratch buffer for commands which also send
     
    12841454        RTMemFree(pvScratchBuf);
    12851455
    1286     VBoxServiceVerbose(3, "Disconnecting client ID=%RU32 ...\n", uClientID);
    1287     VbglR3GuestCtrlDisconnect(uClientID);
     1456    if (uClientID)
     1457    {
     1458        VBoxServiceVerbose(3, "Disconnecting client ID=%RU32 ...\n", uClientID);
     1459        VbglR3GuestCtrlDisconnect(uClientID);
     1460    }
    12881461
    12891462    VBoxServiceVerbose(3, "Session worker returned with rc=%Rrc\n", rc);
     
    17551928                        }
    17561929#else
     1930                        /* Include the session thread ID in the log file name. */
    17571931                        if (RTStrAPrintf(&pszLogNewSuffix, "-%RU32-%RU32-%s",
    17581932                                         pSessionStartupInfo->uSessionID,
     
    17931967                    rc = rc2;
    17941968#ifdef DEBUG
    1795                 VBoxServiceVerbose(4, "rc=%Rrc, session flags=%x\n",
     1969                VBoxServiceVerbose(4, "Argv building rc=%Rrc, session flags=%x\n",
    17961970                                   rc, g_Session.uFlags);
    17971971                char szParmDumpStdOut[32];
     
    20492223    int rc = VINF_SUCCESS;
    20502224
     2225    /*int rc = VbglR3GuestCtrlClose
     2226        if (RT_FAILURE(rc))
     2227            VBoxServiceError("Cancelling pending waits failed; rc=%Rrc\n", rc);*/
     2228
    20512229    PVBOXSERVICECTRLSESSIONTHREAD pSessionThread
    20522230         = RTListGetFirst(pList, VBOXSERVICECTRLSESSIONTHREAD, Node);
     
    21402318                break;
    21412319
     2320#ifdef DEBUG
    21422321            case VBOXSERVICESESSIONOPT_THREAD_ID:
    21432322                /* Not handled. */
    21442323                break;
    2145 
     2324#endif
    21462325            /** @todo Implement help? */
    21472326
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