Changeset 97784 in vbox
- Timestamp:
- Dec 12, 2022 5:54:12 PM (2 years ago)
- svn:sync-xref-src-repo-rev:
- 154855
- Location:
- trunk/src/VBox
- Files:
-
- 6 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Frontends/VirtualBox/src/runtime/UIDnDHandler.cpp
r97718 r97784 83 83 : m_pSession(pSession) 84 84 , m_pParent(pParent) 85 , m_enmOpMode(DNDMODE_UNKNOWN)86 , m_fIsPending(false)87 85 , m_fDataRetrieved(false) 88 86 #ifndef RT_OS_WINDOWS … … 107 105 const QMimeData *pMimeData) 108 106 { 109 LogFlowFunc(("enmOpMode=%RU32, screenID=%RU32, x=%d, y=%d, action=%ld\n", 110 m_enmOpMode, screenID, x, y, toVBoxDnDAction(proposedAction))); 111 112 if ( m_enmOpMode != DNDMODE_UNKNOWN 113 && m_enmOpMode != DNDMODE_HOSTTOGUEST) 114 return Qt::IgnoreAction; 107 LogFlowFunc(("screenID=%RU32, x=%d, y=%d, action=%ld\n", screenID, x, y, toVBoxDnDAction(proposedAction))); 115 108 116 109 /* Ask the guest for starting a DnD event. */ … … 123 116 if (m_dndTarget.isOk()) 124 117 { 125 setOpMode(DNDMODE_HOSTTOGUEST);126 118 return toQtDnDAction(result); 127 119 } … … 134 126 const QMimeData *pMimeData) 135 127 { 136 LogFlowFunc(("enmOpMode=%RU32, screenID=%RU32, x=%d, y=%d, action=%ld\n", 137 m_enmOpMode, screenID, x, y, toVBoxDnDAction(proposedAction))); 138 139 if (m_enmOpMode != DNDMODE_HOSTTOGUEST) 128 LogFlowFunc(("screenID=%RU32, x=%d, y=%d, action=%ld\n", screenID, x, y, toVBoxDnDAction(proposedAction))); 129 130 if (!m_dndTarget.isOk()) /* Don't try any further if we got an error before. */ 140 131 return Qt::IgnoreAction; 141 132 … … 158 149 const QMimeData *pMimeData) 159 150 { 160 LogFlowFunc(("enmOpMode=%RU32, screenID=%RU32, x=%d, y=%d, action=%ld\n", 161 m_enmOpMode, screenID, x, y, toVBoxDnDAction(proposedAction))); 162 163 if (m_enmOpMode != DNDMODE_HOSTTOGUEST) 151 LogFlowFunc(("screenID=%RU32, x=%d, y=%d, action=%ld\n", screenID, x, y, toVBoxDnDAction(proposedAction))); 152 153 if (!m_dndTarget.isOk()) /* Don't try any further if we got an error before. */ 164 154 return Qt::IgnoreAction; 165 155 … … 265 255 } 266 256 267 /*268 * Since the mouse button has been release this in any case marks269 * the end of the current transfer direction. So reset the current270 * mode as well here.271 */272 setOpMode(DNDMODE_UNKNOWN);273 274 257 return toQtDnDAction(enmResult); 275 258 } … … 277 260 void UIDnDHandler::dragLeave(ulong screenID) 278 261 { 279 LogFlowFunc((" enmOpMode=%RU32, screenID=%RU32\n", m_enmOpMode, screenID));280 281 if ( m_enmOpMode == DNDMODE_HOSTTOGUEST)282 {283 m_dndTarget.Leave(screenID); 284 setOpMode(DNDMODE_UNKNOWN);285 }262 LogFlowFunc(("screenID=%RU32\n", screenID)); 263 264 if (!m_dndTarget.isOk()) /* Don't try any further if we got an error before. */ 265 return; 266 267 m_dndTarget.Leave(screenID); 268 return; 286 269 } 287 270 … … 323 306 { 324 307 RT_NOREF(defAction); 308 325 309 int rc = VINF_SUCCESS; 326 310 … … 454 438 } 455 439 440 /** 441 * Checks whether a G->H drag'n drop operation is pending. 442 * 443 * @returns VBox status code. 444 * @retval VERR_NO_DATA if no operation is pending or an error has occurred. 445 * @retval VERR_NOT_SUPPORTED if G->H operations are not supported. 446 * @param screenID Screen ID to check pending status. 447 */ 456 448 int UIDnDHandler::dragCheckPending(ulong screenID) 457 449 { 458 450 int rc; 459 451 #ifdef VBOX_WITH_DRAG_AND_DROP_GH 460 461 LogFlowFunc(("enmOpMode=%RU32, fIsPending=%RTbool, screenID=%RU32\n", m_enmOpMode, m_fIsPending, screenID)); 462 463 { 464 QMutexLocker AutoReadLock(&m_ReadLock); 465 466 if ( m_enmOpMode != DNDMODE_UNKNOWN 467 && m_enmOpMode != DNDMODE_GUESTTOHOST) /* Wrong mode set? */ 468 return VINF_SUCCESS; 469 470 if (m_fIsPending) /* Pending operation is in progress. */ 471 return VINF_SUCCESS; 472 } 473 474 QMutexLocker AutoWriteLock(&m_WriteLock); 475 m_fIsPending = true; 476 AutoWriteLock.unlock(); 452 LogFlowFunc(("screenID=%RU32\n", screenID)); 477 453 478 454 /** … … 496 472 QVector<QString> vecFormats; 497 473 m_dataSource.defaultAction = m_dndSource.DragIsPending(screenID, vecFormats, m_dataSource.vecActions); 474 if (!m_dndSource.isOk()) 475 return VERR_NO_DATA; 498 476 499 477 LogRelMax3(10, ("DnD: Default action is: 0x%x\n", m_dataSource.defaultAction)); … … 526 504 rc = VERR_NO_DATA; 527 505 528 AutoWriteLock.relock();529 m_fIsPending = false;530 AutoWriteLock.unlock();531 532 506 #else /* !VBOX_WITH_DRAG_AND_DROP_GH */ 533 534 NOREF(screenID); 535 507 RT_NOREF(screenID); 536 508 rc = VERR_NOT_SUPPORTED; 537 538 509 #endif /* VBOX_WITH_DRAG_AND_DROP_GH */ 539 510 … … 547 518 #ifdef VBOX_WITH_DRAG_AND_DROP_GH 548 519 549 NOREF(screenID);520 RT_NOREF(screenID); 550 521 551 522 LogFlowFuncEnter(); … … 559 530 } 560 531 561 setOpMode(DNDMODE_GUESTTOHOST);562 563 532 rc = dragStartInternal(m_dataSource.lstFormats, 564 533 toQtDnDAction(m_dataSource.defaultAction), toQtDnDActions(m_dataSource.vecActions)); 565 534 566 535 #else /* !VBOX_WITH_DRAG_AND_DROP_GH */ 567 568 NOREF(screenID); 569 536 RT_NOREF(screenID); 570 537 rc = VERR_NOT_SUPPORTED; 571 572 538 #endif /* VBOX_WITH_DRAG_AND_DROP_GH */ 573 539 … … 578 544 int UIDnDHandler::dragStop(ulong screenID) 579 545 { 546 RT_NOREF(screenID); 580 547 int rc; 581 548 #ifdef VBOX_WITH_DRAG_AND_DROP_GH 582 583 NOREF(screenID);584 585 549 reset(); 586 550 rc = VINF_SUCCESS; 587 588 551 #else /* !VBOX_WITH_DRAG_AND_DROP_GH */ 589 590 NOREF(screenID);591 592 552 rc = VERR_NOT_SUPPORTED; 593 594 553 #endif /* VBOX_WITH_DRAG_AND_DROP_GH */ 595 596 554 LogFlowFuncLeaveRC(rc); 597 555 return rc; … … 603 561 604 562 m_fDataRetrieved = false; 605 m_fIsPending = false;606 607 setOpMode(DNDMODE_UNKNOWN);608 563 } 609 564 … … 720 675 } 721 676 722 setOpMode(DNDMODE_UNKNOWN);723 724 677 LogFlowFuncLeaveRC(rc); 725 678 return rc; 726 }727 728 /**729 * Sets the current DnD operation mode.730 *731 * Note: Only one mode (guest->host *or* host->guest) can be active at the same time.732 *733 * @param enmMode Current operation mode to set.734 */735 void UIDnDHandler::setOpMode(DNDOPMODE enmMode)736 {737 QMutexLocker AutoWriteLock(&m_WriteLock);738 739 /** @todo r=andy Check for old (current) mode and refuse new mode? */740 741 m_enmOpMode = enmMode;742 LogFunc(("Operation mode is now: %RU32\n", m_enmOpMode));743 679 } 744 680 -
trunk/src/VBox/Frontends/VirtualBox/src/runtime/UIDnDHandler.h
r96407 r97784 59 59 UIDnDHandler(UISession *pSession, QWidget *pParent); 60 60 virtual ~UIDnDHandler(void); 61 62 /**63 * Current operation mode.64 * Note: The operation mode is independent of the machine's overall65 * drag and drop mode.66 */67 typedef enum DNDOPMODE68 {69 /** Unknown mode. */70 DNDMODE_UNKNOWN = 0,71 /** Host to guest. */72 DNDMODE_HOSTTOGUEST = 1,73 /** Guest to host. */74 DNDMODE_GUESTTOHOST = 2,75 /** @todo Implement guest to guest. */76 /** The usual 32-bit type blow up. */77 DNDMODE_32BIT_HACK = 0x7fffffff78 } DNDOPMODE;79 61 80 62 /** … … 141 123 int dragStartInternal(const QStringList &lstFormats, Qt::DropAction defAction, Qt::DropActions actions); 142 124 int retrieveDataInternal(Qt::DropAction dropAction, const QString &strMIMEType, QVector<uint8_t> &vecData); 143 void setOpMode(DNDOPMODE enmMode);144 125 145 126 protected: … … 153 134 /** Drag and drop target instance. */ 154 135 CDnDTarget m_dndTarget; 155 /** Current operation mode, indicating the transfer direction.156 * Note: This is independent of the current drag and drop157 * mode being set for this VM! */158 DNDOPMODE m_enmOpMode;159 136 /** Current data from the source (if any). 160 137 * At the momenet we only support one source at a time. */ 161 138 UIDnDDataSource m_dataSource; 162 /** Flag indicating if a drag operation is pending currently. */163 bool m_fIsPending;164 139 /** Flag indicating whether data has been retrieved from 165 140 * the guest already or not. */ -
trunk/src/VBox/Main/include/GuestDnDPrivate.h
r97783 r97784 821 821 public: 822 822 823 VBOXDNDSTATE get() { return m_enmState; } const 824 int set(VBOXDNDSTATE enmState) { LogRel3(("DnD: State %s -> %s\n", DnDStateToStr(m_enmState), DnDStateToStr(enmState))); m_enmState = enmState; return 0; } 825 void lock() { RTCritSectEnter(&m_CritSect); }; 826 void unlock() { RTCritSectLeave(&m_CritSect); }; 827 823 828 /** @name Guest response handling. 824 829 * @{ */ … … 856 861 /** Pointer to context this class is tied to. */ 857 862 void *m_pvCtx; 863 RTCRITSECT m_CritSect; 864 /** The current state we're in. */ 865 VBOXDNDSTATE m_enmState; 858 866 /** The DnD protocol version to use, depending on the 859 867 * installed Guest Additions. See DragAndDropSvc.h for -
trunk/src/VBox/Main/src-client/GuestDnDPrivate.cpp
r97783 r97784 301 301 302 302 GuestDnDState::GuestDnDState(const ComObjPtr<Guest>& pGuest) 303 : m_uProtocolVersion(0) 303 : m_enmState(VBOXDNDSTATE_UNKNOWN) 304 , m_uProtocolVersion(0) 304 305 , m_fGuestFeatures0(VBOX_DND_GF_NONE) 305 306 , m_EventSem(NIL_RTSEMEVENT) … … 309 310 , m_pParent(pGuest) 310 311 { 311 int rc = RT SemEventCreate(&m_EventSem);312 int rc = RTCritSectInit(&m_CritSect); 312 313 if (RT_FAILURE(rc)) 313 314 throw rc; 315 rc = RTSemEventCreate(&m_EventSem); 316 if (RT_FAILURE(rc)) 317 throw rc; 314 318 } 315 319 … … 320 324 int rc = RTSemEventDestroy(m_EventSem); 321 325 AssertRC(rc); 326 rc = RTCritSectDelete(&m_CritSect); 327 AssertRC(rc); 322 328 } 323 329 … … 336 342 337 343 /** 338 * Resets a GuestDnDResponse object.344 * Resets a guest drag'n drop state. 339 345 */ 340 346 void GuestDnDState::reset(void) 341 347 { 342 LogFlowThisFuncEnter(); 343 344 m_dndActionDefault = 0; 345 m_dndLstActionsAllowed = 0; 348 LogRel2(("DnD: Reset\n")); 349 350 m_enmState = VBOXDNDSTATE_UNKNOWN; 351 352 m_dndActionDefault = VBOX_DND_ACTION_IGNORE; 353 m_dndLstActionsAllowed = VBOX_DND_ACTION_IGNORE; 346 354 347 355 m_lstFormats.clear(); -
trunk/src/VBox/Main/src-client/GuestDnDSourceImpl.cpp
r97783 r97784 286 286 287 287 GuestDnDState *pState = GuestDnDInst()->getState(); 288 AssertPtrReturn(pState, E_POINTER); 288 AssertPtr(pState); 289 290 /* Check if any operation is active, and if so, bail out, returning an ignore action (see above). */ 291 if (pState->get() != VBOXDNDSTATE_UNKNOWN) 292 return S_OK; 293 294 pState->set(VBOXDNDSTATE_QUERY_FORMATS); 289 295 290 296 HRESULT hrc = S_OK; … … 339 345 else 340 346 hrc = i_setErrorAndReset(vrc, tr("Sending drag pending event to guest failed")); 347 348 pState->set(VBOXDNDSTATE_UNKNOWN); 341 349 342 350 LogFlowFunc(("hr=%Rhrc\n", hrc)); -
trunk/src/VBox/Main/src-client/GuestDnDTargetImpl.cpp
r97783 r97784 350 350 LogRel2(("DnD: Host enters the VM window at %RU32,%RU32 (screen %u, default action is '%s') -> guest reported back action '%s'\n", 351 351 aX, aY, aScreenId, DnDActionToStr(dndActionDefault), DnDActionToStr(resAction))); 352 353 pState->set(VBOXDNDSTATE_ENTERED); 352 354 } 353 355 else … … 455 457 LogRel2(("DnD: Host moved to %RU32,%RU32 in VM window (screen %u, default action is '%s') -> guest reported back action '%s'\n", 456 458 aX, aY, aScreenId, DnDActionToStr(dndActionDefault), DnDActionToStr(resAction))); 459 460 pState->set(VBOXDNDSTATE_DRAGGING); 457 461 } 458 462 else … … 510 514 AssertPtrReturn(pState, E_POINTER); 511 515 516 if (pState->get() == VBOXDNDSTATE_DROP_STARTED) 517 return S_OK; 518 512 519 HRESULT hrc = S_OK; 513 520 … … 525 532 if (RT_SUCCESS(vrc = pState->waitForGuestResponse(&vrcGuest))) 526 533 { 527 /* Nothing to do here. */534 pState->set(VBOXDNDSTATE_LEFT); 528 535 } 529 536 else … … 644 651 { 645 652 resFmt = lstFormats.at(0); 653 654 LogRel2(("DnD: Guest accepted drop in format '%s' (action %#x, %zu format(s))\n", 655 resFmt.c_str(), resAct, lstFormats.size())); 656 657 pState->set(VBOXDNDSTATE_DROP_STARTED); 646 658 } 647 659 else … … 916 928 } 917 929 918 if (RT_FAILURE(vrc)) 919 { 920 LogRel(("DnD: Sending data to guest failed with %Rrc\n", vrc)); 930 GuestDnDState *pState = GuestDnDInst()->getState(); 931 AssertPtrReturn(pState, E_POINTER); 932 933 if (RT_SUCCESS(vrc)) 934 { 935 pState->set(VBOXDNDSTATE_DROP_ENDED); 936 } 937 else 938 { 939 if (vrc == VERR_CANCELLED) 940 { 941 LogRel(("DnD: Sending data to guest cancelled by the user\n")); 942 pState->set(VBOXDNDSTATE_CANCELLED); 943 } 944 else 945 { 946 LogRel(("DnD: Sending data to guest failed with %Rrc\n", vrc)); 947 pState->set(VBOXDNDSTATE_ERROR); 948 } 949 950 /* Make sure to fire a cancel request to the guest side in any case to prevent any guest side hangs. */ 921 951 sendCancel(); 922 952 }
Note:
See TracChangeset
for help on using the changeset viewer.