Exemple #1
0
/* static */
DECLCALLBACK(int) Guest::i_notifyCtrlDispatcher(void    *pvExtension,
                                                uint32_t u32Function,
                                                void    *pvData,
                                                uint32_t cbData)
{
    using namespace guestControl;

    /*
     * No locking, as this is purely a notification which does not make any
     * changes to the object state.
     */
    LogFlowFunc(("pvExtension=%p, u32Function=%RU32, pvParms=%p, cbParms=%RU32\n",
                 pvExtension, u32Function, pvData, cbData));
    ComObjPtr<Guest> pGuest = reinterpret_cast<Guest *>(pvExtension);
    Assert(!pGuest.isNull());

    /*
     * For guest control 2.0 using the legacy commands we need to do the following here:
     * - Get the callback header to access the context ID
     * - Get the context ID of the callback
     * - Extract the session ID out of the context ID
     * - Dispatch the whole stuff to the appropriate session (if still exists)
     */
    if (cbData != sizeof(VBOXGUESTCTRLHOSTCALLBACK))
        return VERR_NOT_SUPPORTED;
    PVBOXGUESTCTRLHOSTCALLBACK pSvcCb = (PVBOXGUESTCTRLHOSTCALLBACK)pvData;
    AssertPtr(pSvcCb);

    if (!pSvcCb->mParms) /* At least context ID must be present. */
        return VERR_INVALID_PARAMETER;

    uint32_t uContextID;
    int rc = pSvcCb->mpaParms[0].getUInt32(&uContextID);
    AssertMsgRCReturn(rc, ("Unable to extract callback context ID, pvData=%p\n", pSvcCb), rc);
#ifdef DEBUG
    LogFlowFunc(("CID=%RU32, uSession=%RU32, uObject=%RU32, uCount=%RU32\n",
                 uContextID,
                 VBOX_GUESTCTRL_CONTEXTID_GET_SESSION(uContextID),
                 VBOX_GUESTCTRL_CONTEXTID_GET_OBJECT(uContextID),
                 VBOX_GUESTCTRL_CONTEXTID_GET_COUNT(uContextID)));
#endif

    VBOXGUESTCTRLHOSTCBCTX ctxCb = { u32Function, uContextID };
    rc = pGuest->i_dispatchToSession(&ctxCb, pSvcCb);

    LogFlowFunc(("Returning rc=%Rrc\n", rc));
    return rc;
}
/* static */
DECLCALLBACK(int) Guest::i_notifyCtrlDispatcher(void    *pvExtension,
                                                uint32_t idMessage,
                                                void    *pvData,
                                                uint32_t cbData)
{
    using namespace guestControl;

    /*
     * No locking, as this is purely a notification which does not make any
     * changes to the object state.
     */
    Log2Func(("pvExtension=%p, idMessage=%RU32, pvParms=%p, cbParms=%RU32\n", pvExtension, idMessage, pvData, cbData));

    ComObjPtr<Guest> pGuest = reinterpret_cast<Guest *>(pvExtension);
    AssertReturn(pGuest.isNotNull(), VERR_WRONG_ORDER);

    /*
     * The data packet should ever be a problem, but check to be sure.
     */
    AssertMsgReturn(cbData == sizeof(VBOXGUESTCTRLHOSTCALLBACK),
                    ("Guest control host callback data has wrong size (expected %zu, got %zu) - buggy host service!\n",
                     sizeof(VBOXGUESTCTRLHOSTCALLBACK), cbData), VERR_INVALID_PARAMETER);
    PVBOXGUESTCTRLHOSTCALLBACK pSvcCb = (PVBOXGUESTCTRLHOSTCALLBACK)pvData;
    AssertPtrReturn(pSvcCb, VERR_INVALID_POINTER);

    /*
     * For guest control 2.0 using the legacy messages we need to do the following here:
     * - Get the callback header to access the context ID
     * - Get the context ID of the callback
     * - Extract the session ID out of the context ID
     * - Dispatch the whole stuff to the appropriate session (if still exists)
     *
     * At least context ID parameter must always be present.
     */
    ASSERT_GUEST_RETURN(pSvcCb->mParms > 0, VERR_WRONG_PARAMETER_COUNT);
    ASSERT_GUEST_MSG_RETURN(pSvcCb->mpaParms[0].type == VBOX_HGCM_SVC_PARM_32BIT,
                            ("type=%d\n", pSvcCb->mpaParms[0].type), VERR_WRONG_PARAMETER_TYPE);
    uint32_t const idContext = pSvcCb->mpaParms[0].u.uint32;

    VBOXGUESTCTRLHOSTCBCTX CtxCb = { idMessage, idContext };
    int rc = pGuest->i_dispatchToSession(&CtxCb, pSvcCb);

    Log2Func(("CID=%#x, idSession=%RU32, uObject=%RU32, uCount=%RU32, rc=%Rrc\n",
              idContext, VBOX_GUESTCTRL_CONTEXTID_GET_SESSION(idContext), VBOX_GUESTCTRL_CONTEXTID_GET_OBJECT(idContext),
              VBOX_GUESTCTRL_CONTEXTID_GET_COUNT(idContext), rc));
    return rc;
}