void Light::tick() { if (NORMAL == modeGet()) return; if (waiting()) return; if (OFF == stateGet()) on(); else off(); wait(interval); }
int DragAndDropService::hostCall(uint32_t u32Function, uint32_t cParms, VBOXHGCMSVCPARM paParms[]) { int rc = VINF_SUCCESS; if (u32Function == DragAndDropSvc::HOST_DND_SET_MODE) { if (cParms != 1) rc = VERR_INVALID_PARAMETER; else if (paParms[0].type != VBOX_HGCM_SVC_PARM_32BIT) rc = VERR_INVALID_PARAMETER; else modeSet(paParms[0].u.uint32); } else if (modeGet() != VBOX_DRAG_AND_DROP_MODE_OFF) { rc = m_pManager->addMessage(u32Function, cParms, paParms); if ( RT_SUCCESS(rc) && !m_clientQueue.isEmpty()) { HGCM::Client *pClient = m_clientQueue.first(); /* Check if this was a request for getting the next host * message. If so, return the message id and the parameter * count. The message itself has to be queued. */ if (pClient->message() == DragAndDropSvc::GUEST_DND_GET_NEXT_HOST_MSG) { DO(("client is waiting for next host msg\n")); // rc = m_pManager->nextMessageInfo(&paParms[0].u.uint32, &paParms[1].u.uint32); uint32_t uMsg1; uint32_t cParms1; rc = m_pManager->nextMessageInfo(&uMsg1, &cParms1); if (RT_SUCCESS(rc)) { pClient->addMessageInfo(uMsg1, cParms1); m_pHelpers->pfnCallComplete(pClient->handle(), rc); m_clientQueue.removeFirst(); delete pClient; } else AssertMsgFailed(("Should not happen!")); } else AssertMsgFailed(("Should not happen!")); } // else // AssertMsgFailed(("Should not happen %Rrc!", rc)); } LogFlowFunc(("rc=%Rrc\n", rc)); return rc; }
void DragAndDropService::guestCall(VBOXHGCMCALLHANDLE callHandle, uint32_t u32ClientID, void *pvClient, uint32_t u32Function, uint32_t cParms, VBOXHGCMSVCPARM paParms[]) { int rc = VINF_SUCCESS; LogFlowFunc(("u32ClientID = %d, fn = %d, cParms = %d, pparms = %d\n", u32ClientID, u32Function, cParms, paParms)); // RTPrintf("u32ClientID = %d, fn = %d, cParms = %d, pparms = %d\n", // u32ClientID, u32Function, cParms, paParms); switch (u32Function) { case DragAndDropSvc::GUEST_DND_GET_NEXT_HOST_MSG: { DO(("GUEST_DND_GET_NEXT_HOST_MSG\n")); if ( cParms != 3 || paParms[0].type != VBOX_HGCM_SVC_PARM_32BIT /* message */ || paParms[1].type != VBOX_HGCM_SVC_PARM_32BIT /* parameter count */ || paParms[2].type != VBOX_HGCM_SVC_PARM_32BIT /* blocking */) rc = VERR_INVALID_PARAMETER; else { rc = m_pManager->nextMessageInfo(&paParms[0].u.uint32, &paParms[1].u.uint32); if ( RT_FAILURE(rc) && paParms[2].u.uint32) /* Blocking? */ { m_clientQueue.append(new HGCM::Client(u32ClientID, callHandle, u32Function, cParms, paParms)); rc = VINF_HGCM_ASYNC_EXECUTE; } } break; } case DragAndDropSvc::GUEST_DND_HG_ACK_OP: { DO(("GUEST_DND_HG_ACK_OP\n")); if ( modeGet() != VBOX_DRAG_AND_DROP_MODE_BIDIRECTIONAL && modeGet() != VBOX_DRAG_AND_DROP_MODE_HOST_TO_GUEST) { DO(("=> ignoring!\n")); break; } if ( cParms != 1 || paParms[0].type != VBOX_HGCM_SVC_PARM_32BIT /* action */) rc = VERR_INVALID_PARAMETER; else { DragAndDropSvc::VBOXDNDCBHGACKOPDATA data; data.hdr.u32Magic = DragAndDropSvc::CB_MAGIC_DND_HG_ACK_OP; paParms[0].getUInt32(&data.uAction); if (m_pfnHostCallback) rc = m_pfnHostCallback(m_pvHostData, u32Function, &data, sizeof(data)); // m_pHelpers->pfnCallComplete(callHandle, rc); } break; } case DragAndDropSvc::GUEST_DND_HG_REQ_DATA: { DO(("GUEST_DND_HG_REQ_DATA\n")); if ( modeGet() != VBOX_DRAG_AND_DROP_MODE_BIDIRECTIONAL && modeGet() != VBOX_DRAG_AND_DROP_MODE_HOST_TO_GUEST) { DO(("=> ignoring!\n")); break; } if ( cParms != 1 || paParms[0].type != VBOX_HGCM_SVC_PARM_PTR /* format */) rc = VERR_INVALID_PARAMETER; else { DragAndDropSvc::VBOXDNDCBHGREQDATADATA data; data.hdr.u32Magic = DragAndDropSvc::CB_MAGIC_DND_HG_REQ_DATA; uint32_t cTmp; paParms[0].getPointer((void**)&data.pszFormat, &cTmp); if (m_pfnHostCallback) rc = m_pfnHostCallback(m_pvHostData, u32Function, &data, sizeof(data)); // m_pHelpers->pfnCallComplete(callHandle, rc); // if (data.pszFormat) // RTMemFree(data.pszFormat); // if (data.pszTmpPath) // RTMemFree(data.pszTmpPath); } break; } #ifdef VBOX_WITH_DRAG_AND_DROP_GH case DragAndDropSvc::GUEST_DND_GH_ACK_PENDING: { DO(("GUEST_DND_GH_ACK_PENDING\n")); if ( modeGet() != VBOX_DRAG_AND_DROP_MODE_BIDIRECTIONAL && modeGet() != VBOX_DRAG_AND_DROP_MODE_GUEST_TO_HOST) { DO(("=> ignoring!\n")); break; } if ( cParms != 3 || paParms[0].type != VBOX_HGCM_SVC_PARM_32BIT /* defaction */ || paParms[1].type != VBOX_HGCM_SVC_PARM_32BIT /* allactions */ || paParms[2].type != VBOX_HGCM_SVC_PARM_PTR /* format */) rc = VERR_INVALID_PARAMETER; else { DragAndDropSvc::VBOXDNDCBGHACKPENDINGDATA data; data.hdr.u32Magic = DragAndDropSvc::CB_MAGIC_DND_GH_ACK_PENDING; paParms[0].getUInt32(&data.uDefAction); paParms[1].getUInt32(&data.uAllActions); uint32_t cTmp; paParms[2].getPointer((void**)&data.pszFormat, &cTmp); if (m_pfnHostCallback) rc = m_pfnHostCallback(m_pvHostData, u32Function, &data, sizeof(data)); } break; } case DragAndDropSvc::GUEST_DND_GH_SND_DATA: { DO(("GUEST_DND_GH_SND_DATA\n")); if ( modeGet() != VBOX_DRAG_AND_DROP_MODE_BIDIRECTIONAL && modeGet() != VBOX_DRAG_AND_DROP_MODE_GUEST_TO_HOST) { DO(("=> ignoring\n")); break; } if ( cParms != 2 || paParms[0].type != VBOX_HGCM_SVC_PARM_PTR /* data */ || paParms[1].type != VBOX_HGCM_SVC_PARM_32BIT /* size */) rc = VERR_INVALID_PARAMETER; else { DragAndDropSvc::VBOXDNDCBSNDDATADATA data; data.hdr.u32Magic = DragAndDropSvc::CB_MAGIC_DND_GH_SND_DATA; paParms[0].getPointer((void**)&data.pvData, &data.cbData); paParms[1].getUInt32(&data.cbAllSize); if (m_pfnHostCallback) rc = m_pfnHostCallback(m_pvHostData, u32Function, &data, sizeof(data)); } break; } case DragAndDropSvc::GUEST_DND_GH_EVT_ERROR: { DO(("GUEST_DND_GH_EVT_ERROR\n")); if ( modeGet() != VBOX_DRAG_AND_DROP_MODE_BIDIRECTIONAL && modeGet() != VBOX_DRAG_AND_DROP_MODE_GUEST_TO_HOST) { DO(("=> ignoring!\n")); break; } if ( cParms != 1 || paParms[0].type != VBOX_HGCM_SVC_PARM_32BIT /* rc */) rc = VERR_INVALID_PARAMETER; else { DragAndDropSvc::VBOXDNDCBEVTERRORDATA data; data.hdr.u32Magic = DragAndDropSvc::CB_MAGIC_DND_GH_EVT_ERROR; uint32_t rcOp; paParms[0].getUInt32(&rcOp); data.rc = rcOp; if (m_pfnHostCallback) rc = m_pfnHostCallback(m_pvHostData, u32Function, &data, sizeof(data)); } break; } #endif default: { /* All other messages are handled by the DnD manager. */ rc = m_pManager->nextMessage(u32Function, cParms, paParms); /* Check for error. Buffer overflow is allowed. It signals the * guest to ask for more data in the next event. */ if ( RT_FAILURE(rc) && rc != VERR_CANCELLED && rc != VERR_BUFFER_OVERFLOW) /* Buffer overflow is allowed. */ { m_clientQueue.append(new HGCM::Client(u32ClientID, callHandle, u32Function, cParms, paParms)); rc = VINF_HGCM_ASYNC_EXECUTE; } break; } } /* If async execute is requested, we didn't notify the guest about * completion. The client is queued into the waiters list and will be * notified as soon as a new event is available. */ if (rc != VINF_HGCM_ASYNC_EXECUTE) m_pHelpers->pfnCallComplete(callHandle, rc); DO(("guest call: %Rrc\n", rc)); }