VirtualBox

Changeset 13580 in vbox for trunk/src/VBox/Main/include


Ignore:
Timestamp:
Oct 27, 2008 2:04:18 PM (16 years ago)
Author:
vboxsync
Message:

Ported s2 branch (r37120:38456).

Location:
trunk/src/VBox/Main/include
Files:
3 added
3 deleted
13 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Main/include/AutoLock.h

    r8639 r13580  
    647647
    648648    /**
     649     * Same as #leave() but checks if the current thread actally owns the lock
     650     * and only proceeds in this case. As a result, as opposed to #leave(),
     651     * doesn't assert when called with no lock being held.
     652     */
     653    void maybeLeave()
     654    {
     655        if (isWriteLockOnCurrentThread())
     656            leave();
     657    }
     658
     659    /**
     660     * Same as #enter() but checks if the current thread actally owns the lock
     661     * and only proceeds if not. As a result, as opposed to #enter(), doesn't
     662     * assert when called with the lock already being held.
     663     */
     664    void maybeEnter()
     665    {
     666        if (!isWriteLockOnCurrentThread())
     667            enter();
     668    }
     669
     670    /**
    649671     * Causes the current thread to restore the write lock level after the
    650672     * #leave() call. This call will indefinitely block if another thread has
     
    663685        }
    664686    }
     687
     688    /**
     689     * Attaches another handle to this auto lock instance.
     690     *
     691     * The previous object's lock is completely released before the new one is
     692     * acquired. The lock level of the new handle will be the same. This
     693     * also means that if the lock was not acquired at all before #attach(), it
     694     * will not be acquired on the new handle too.
     695     *
     696     * @param aHandle   New handle to attach.
     697     */
     698    void attach (LockHandle *aHandle)
     699    {
     700        /* detect simple self-reattachment */
     701        if (mHandle != aHandle)
     702        {
     703            uint32_t lockLevel = mLockLevel;
     704
     705            /* perform the destructor part */
     706            if (mHandle)
     707            {
     708                if (mGlobalLockLevel)
     709                {
     710                    mGlobalLockLevel -= mLockLevel;
     711                    mLockLevel = 0;
     712                    for (; mGlobalLockLevel; -- mGlobalLockLevel)
     713                        mHandle->lockWrite();
     714                }
     715
     716                AssertMsg (mLockLevel <= 1, ("Lock level > 1: %d\n", mLockLevel));
     717                for (; mLockLevel; -- mLockLevel)
     718                    mHandle->unlockWrite();
     719            }
     720
     721            mHandle = aHandle;
     722            mLockLevel = lockLevel;
     723
     724            if (mHandle)
     725                for (; lockLevel; -- lockLevel)
     726                    mHandle->lockWrite();
     727        }
     728    }
     729
     730    /** @see attach (LockHandle *) */
     731    void attach (LockHandle &aHandle) { attach (&aHandle); }
     732
     733    /** @see attach (LockHandle *) */
     734    void attach (const Lockable &aLockable) { attach (aLockable.lockHandle()); }
     735
     736    /** @see attach (LockHandle *) */
     737    void attach (const Lockable *aLockable)
     738    { attach (aLockable ? aLockable->lockHandle() : NULL); }
     739
     740    /** Verbose equivalent to <tt>attach (NULL)</tt>. */
     741    void detach() { attach ((LockHandle *) NULL); }
    665742
    666743    /** Returns @c true if this instance manages a null semaphore handle. */
     
    916993        }
    917994    }
     995
     996    /**
     997     * Attaches another handle to this auto lock instance.
     998     *
     999     * The previous object's lock is completely released before the new one is
     1000     * acquired. The lock level of the new handle will be the same. This also
     1001     * means that if the lock was not acquired at all before #attach(), it will
     1002     * not be acquired on the new handle too.
     1003     *
     1004     * @param aHandle   New handle to attach.
     1005     */
     1006    void attach (LockHandle *aHandle)
     1007    {
     1008        /* detect simple self-reattachment */
     1009        if (mHandle != aHandle)
     1010        {
     1011            uint32_t lockLevel = mLockLevel;
     1012            if (mHandle)
     1013                for (; mLockLevel; -- mLockLevel)
     1014                    mHandle->unlockRead();
     1015            mHandle = aHandle;
     1016            mLockLevel = lockLevel;
     1017            if (mHandle)
     1018                for (; lockLevel; -- lockLevel)
     1019                    mHandle->lockRead();
     1020        }
     1021    }
     1022
     1023    /** @see attach (LockHandle *) */
     1024    void attach (LockHandle &aHandle) { attach (&aHandle); }
     1025
     1026    /** @see attach (LockHandle *) */
     1027    void attach (const Lockable &aLockable) { attach (aLockable.lockHandle()); }
     1028
     1029    /** @see attach (LockHandle *) */
     1030    void attach (const Lockable *aLockable)
     1031    { attach (aLockable ? aLockable->lockHandle() : NULL); }
     1032
     1033    /** Verbose equivalent to <tt>attach (NULL)</tt>. */
     1034    void detach() { attach ((LockHandle *) NULL); }
    9181035
    9191036    /** Returns @c true if this instance manages a null semaphore handle. */
     
    11581275            mLocks [-- i].leave();
    11591276        while (i != 0);
     1277    }
     1278
     1279    /**
     1280    * Calls AutoWriteLock::maybeLeave() methods for all managed semaphore
     1281    * handles in reverse to the order they were passed to the constructor.
     1282     */
     1283    void maybeLeave()
     1284    {
     1285        AssertReturnVoid (ELEMENTS (mLocks) > 0);
     1286        size_t i = ELEMENTS (mLocks);
     1287        do
     1288            mLocks [-- i].maybeLeave();
     1289        while (i != 0);
     1290    }
     1291
     1292    /**
     1293     * Calls AutoWriteLock::maybeEnter() methods for all managed semaphore
     1294     * handles in order they were passed to the constructor.
     1295     */
     1296    void maybeEnter()
     1297    {
     1298        size_t i = 0;
     1299        while (i < ELEMENTS (mLocks))
     1300            mLocks [i ++].maybeEnter();
    11601301    }
    11611302
  • trunk/src/VBox/Main/include/ConsoleImpl.h

    r13377 r13580  
     1/* $Id$ */
     2
    13/** @file
    24 *
     
    57
    68/*
    7  * Copyright (C) 2006-2007 Sun Microsystems, Inc.
     9 * Copyright (C) 2006-2008 Sun Microsystems, Inc.
    810 *
    911 * This file is part of VirtualBox Open Source Edition (OSE), as
  • trunk/src/VBox/Main/include/DVDDriveImpl.h

    r8155 r13580  
    77
    88/*
    9  * Copyright (C) 2006-2007 Sun Microsystems, Inc.
     9 * Copyright (C) 2006-2008 Sun Microsystems, Inc.
    1010 *
    1111 * This file is part of VirtualBox Open Source Edition (OSE), as
     
    2727#include "VirtualBoxBase.h"
    2828
     29#include "MediumImpl.h"
     30
    2931class Machine;
    3032
     
    3941    struct Data
    4042    {
    41         Data() {
    42             mDriveState = DriveState_NotMounted;
     43        Data()
     44        {
     45            mState = DriveState_NotMounted;
    4346            mPassthrough = false;
    4447        }
     
    4750        {
    4851            return this == &that ||
    49                    (mDriveState == that.mDriveState &&
    50                     mDVDImage.equalsTo (that.mDVDImage) &&
     52                   (mState == that.mState &&
     53                    mImage.equalsTo (that.mImage) &&
    5154                    mHostDrive.equalsTo (that.mHostDrive));
    5255        }
    5356
    54         ComPtr <IDVDImage> mDVDImage;
     57        ComObjPtr <DVDImage2> mImage;
    5558        ComPtr <IHostDVDDrive> mHostDrive;
    56         DriveState_T mDriveState;
     59        DriveState_T mState;
    5760        BOOL mPassthrough;
    5861    };
     
    8386
    8487    // IDVDDrive properties
    85     STDMETHOD(COMGETTER(State)) (DriveState_T *aDriveState);
     88    STDMETHOD(COMGETTER(State)) (DriveState_T *aState);
    8689    STDMETHOD(COMGETTER(Passthrough)) (BOOL *aPassthrough);
    8790    STDMETHOD(COMSETTER(Passthrough)) (BOOL aPassthrough);
     
    9194    STDMETHOD(CaptureHostDrive) (IHostDVDDrive *aHostDVDDrive);
    9295    STDMETHOD(Unmount)();
    93     STDMETHOD(GetImage) (IDVDImage **aDVDImage);
     96    STDMETHOD(GetImage) (IDVDImage2 **aDVDImage);
    9497    STDMETHOD(GetHostDrive) (IHostDVDDrive **aHostDVDDrive);
    9598
  • trunk/src/VBox/Main/include/FloppyDriveImpl.h

    r8155 r13580  
    77
    88/*
    9  * Copyright (C) 2006-2007 Sun Microsystems, Inc.
     9 * Copyright (C) 2006-2008 Sun Microsystems, Inc.
    1010 *
    1111 * This file is part of VirtualBox Open Source Edition (OSE), as
     
    2727#include "VirtualBoxBase.h"
    2828
     29#include "MediumImpl.h"
     30
    2931class Machine;
    3032
     
    4244        {
    4345            mEnabled    = true;
    44             mDriveState = DriveState_NotMounted;
     46            mState = DriveState_NotMounted;
    4547        }
    4648
     
    4850        {
    4951            return this == &that ||
    50                    (mDriveState == that.mDriveState &&
    51                     mFloppyImage.equalsTo (that.mFloppyImage) &&
     52                   (mState == that.mState &&
     53                    mImage.equalsTo (that.mImage) &&
    5254                    mHostDrive.equalsTo (that.mHostDrive));
    5355        }
    5456
    5557        BOOL mEnabled;
    56         ComPtr <IFloppyImage> mFloppyImage;
     58        ComObjPtr <FloppyImage2> mImage;
    5759        ComPtr <IHostFloppyDrive> mHostDrive;
    58         DriveState_T mDriveState;
     60        DriveState_T mState;
    5961    };
    6062
     
    8688    STDMETHOD(COMGETTER(Enabled)) (BOOL *aEnabled);
    8789    STDMETHOD(COMSETTER(Enabled)) (BOOL aEnabled);
    88     STDMETHOD(COMGETTER(State)) (DriveState_T *aDriveState);
     90    STDMETHOD(COMGETTER(State)) (DriveState_T *aState);
    8991
    9092    // IFloppyDrive methods
     
    9294    STDMETHOD(CaptureHostDrive) (IHostFloppyDrive *aHostFloppyDrive);
    9395    STDMETHOD(Unmount)();
    94     STDMETHOD(GetImage) (IFloppyImage **aFloppyImage);
     96    STDMETHOD(GetImage) (IFloppyImage2 **aFloppyImage);
    9597    STDMETHOD(GetHostDrive) (IHostFloppyDrive **aHostFloppyDrive);
    9698
  • trunk/src/VBox/Main/include/GuestOSTypeImpl.h

    r8155 r13580  
    3636public:
    3737
    38     VIRTUALBOXBASE_ADD_ERRORINFO_SUPPORT (DVDImage)
     38    VIRTUALBOXBASE_ADD_ERRORINFO_SUPPORT (GuestOSType)
    3939
    4040    DECLARE_NOT_AGGREGATABLE(GuestOSType)
  • trunk/src/VBox/Main/include/HardDiskAttachmentImpl.h

    r8155 r13580  
    2424
    2525#include "VirtualBoxBase.h"
    26 #include "Collection.h"
    2726
    28 #include "HardDiskImpl.h"
     27#include "HardDisk2Impl.h"
    2928
    30 class ATL_NO_VTABLE HardDiskAttachment :
    31     public VirtualBoxSupportErrorInfoImpl <HardDiskAttachment, IHardDiskAttachment>,
    32     public VirtualBoxSupportTranslation <HardDiskAttachment>,
    33     public VirtualBoxBase,
    34     public IHardDiskAttachment
     29class ATL_NO_VTABLE HardDisk2Attachment :
     30    public VirtualBoxBaseNEXT,
     31    public com::SupportErrorInfoImpl <HardDisk2Attachment, IHardDisk2Attachment>,
     32    public VirtualBoxSupportTranslation <HardDisk2Attachment>,
     33    public IHardDisk2Attachment
    3534{
    3635public:
    3736
    38     DECLARE_EMPTY_CTOR_DTOR (HardDiskAttachment)
     37    /** Equality predicate for stdc++. */
     38    struct EqualsTo
     39        : public std::unary_function <ComObjPtr <HardDisk2Attachment>, bool>
     40    {
     41        explicit EqualsTo (StorageBus_T aBus, LONG aChannel, LONG aDevice)
     42            : bus (aBus), channel (aChannel), device (aDevice) {}
    3943
    40     DECLARE_NOT_AGGREGATABLE(HardDiskAttachment)
     44        bool operator() (const argument_type &aThat) const
     45        {
     46            return aThat->bus() == bus && aThat->channel() == channel &&
     47                   aThat->device() == device;
     48        }
     49
     50        const StorageBus_T bus;
     51        const LONG channel;
     52        const LONG device;
     53    };
     54
     55    /** Hard disk reference predicate for stdc++. */
     56    struct RefersTo
     57        : public std::unary_function <ComObjPtr <HardDisk2Attachment>, bool>
     58    {
     59        explicit RefersTo (HardDisk2 *aHardDisk) : hardDisk (aHardDisk) {}
     60
     61        bool operator() (const argument_type &aThat) const
     62        {
     63            return aThat->hardDisk().equalsTo (hardDisk);
     64        }
     65
     66        const ComObjPtr <HardDisk2> hardDisk;
     67    };
     68
     69    DECLARE_NOT_AGGREGATABLE(HardDisk2Attachment)
    4170
    4271    DECLARE_PROTECT_FINAL_CONSTRUCT()
    4372
    44     BEGIN_COM_MAP(HardDiskAttachment)
     73    BEGIN_COM_MAP (HardDisk2Attachment)
    4574        COM_INTERFACE_ENTRY(ISupportErrorInfo)
    46         COM_INTERFACE_ENTRY(IHardDiskAttachment)
     75        COM_INTERFACE_ENTRY(IHardDisk2Attachment)
    4776    END_COM_MAP()
    4877
     
    5382
    5483    // public initializer/uninitializer for internal purposes only
    55     HRESULT init (HardDisk *aHD, StorageBus_T aBus, LONG aChannel, LONG aDevice, BOOL aDirty);
     84    HRESULT init (HardDisk2 *aHD, StorageBus_T aBus, LONG aChannel,
     85                  LONG aDevice, bool aImplicit = false);
     86    void uninit();
    5687
    57     // IHardDiskAttachment properties
    58     STDMETHOD(COMGETTER(HardDisk))   (IHardDisk **aHardDisk);
     88    // IHardDisk2Attachment properties
     89    STDMETHOD(COMGETTER(HardDisk))   (IHardDisk2 **aHardDisk);
    5990    STDMETHOD(COMGETTER(Bus))        (StorageBus_T *aBus);
    6091    STDMETHOD(COMGETTER(Channel))    (LONG *aChannel);
    6192    STDMETHOD(COMGETTER(Device))     (LONG *aDevice);
    6293
    63     // public methods for internal purposes only
    64     // (ensure there is a caller and a read or write lock before calling them!)
     94    // unsafe inline public methods for internal purposes only (ensure there is
     95    // a caller and a read lock before calling them!)
    6596
    66     BOOL isDirty() const { return mDirty; }
    67     void setDirty (BOOL aDirty) { mDirty = aDirty; }
     97    bool isImplicit() const { return m.implicit; }
     98    void setImplicit (bool aImplicit) { m.implicit = aImplicit; }
    6899
    69     const ComObjPtr <HardDisk> &hardDisk() const { return mHardDisk; }
    70     StorageBus_T bus() const { return mBus; }
    71     LONG channel() const { return mChannel; }
    72     LONG device() const { return mDevice; }
     100    const ComObjPtr <HardDisk2> &hardDisk() const { return m.hardDisk; }
     101    StorageBus_T bus() const { return m.bus; }
     102    LONG channel() const { return m.channel; }
     103    LONG device() const { return m.device; }
    73104
    74     void updateHardDisk (const ComObjPtr <HardDisk> &aHardDisk, BOOL aDirty)
     105    /** Must be called from under this object's write lock.  */
     106    void updateHardDisk (const ComObjPtr <HardDisk2> &aHardDisk, bool aImplicit)
    75107    {
    76         mHardDisk = aHardDisk;
    77         mDirty = aDirty;
     108        m.hardDisk = aHardDisk;
     109        m.implicit = aImplicit;
    78110    }
    79111
    80     // for VirtualBoxSupportErrorInfoImpl
    81     static const wchar_t *getComponentName() { return L"HardDiskAttachment"; }
     112    /** For com::SupportErrorInfoImpl. */
     113    static const char *ComponentName() { return "HardDisk2Attachment"; }
    82114
    83115private:
    84116
    85     BOOL mDirty;
    86     ComObjPtr <HardDisk> mHardDisk;
    87     StorageBus_T mBus;
    88     LONG mChannel;
    89     LONG mDevice;
     117    struct Data
     118    {
     119        Data() : bus (StorageBus_Null), channel (0), device (0)
     120               , implicit (false) {}
     121
     122        /// @todo NEWMEDIA shouldn't it be constant too? It'd be nice to get
     123        /// rid of locks at all in this simple readonly structure-like interface
     124        ComObjPtr <HardDisk2> hardDisk;
     125        const StorageBus_T bus;
     126        const LONG channel;
     127        const LONG device;
     128
     129        bool implicit : 1;
     130    };
     131
     132    Data m;
    90133};
    91134
    92 COM_DECL_READONLY_ENUM_AND_COLLECTION (HardDiskAttachment)
    93 
    94135#endif // ____H_HARDDISKATTACHMENTIMPL
  • trunk/src/VBox/Main/include/MachineImpl.h

    r13457 r13580  
    8787public:
    8888
     89    enum InstanceType { IsMachine, IsSessionMachine, IsSnapshotMachine };
     90
    8991    /**
    9092     *  Internal machine data.
     
    273275     *
    274276     *  The usage policy is the same as for HWData, but a separate structure
    275      *  is necessarym because hard disk data requires different procedures when
     277     *  is necessary because hard disk data requires different procedures when
    276278     *  taking or discarding snapshots, etc.
    277279     *
     
    285287        bool operator== (const HDData &that) const;
    286288
    287         typedef std::list <ComObjPtr <HardDiskAttachment> > HDAttachmentList;
    288         HDAttachmentList mHDAttachments;
    289 
    290         /**
    291          *  Right after Machine::fixupHardDisks(true): |true| if hard disks
    292          *  were actually changed, |false| otherwise
    293          */
    294         bool mHDAttachmentsChanged;
     289        typedef std::list <ComObjPtr <HardDisk2Attachment> > AttachmentList;
     290        AttachmentList mAttachments;
    295291    };
    296292
     
    497493    STDMETHOD(COMGETTER(SnapshotFolder))(BSTR *aSavedStateFolder);
    498494    STDMETHOD(COMSETTER(SnapshotFolder))(INPTR BSTR aSavedStateFolder);
    499     STDMETHOD(COMGETTER(HardDiskAttachments))(IHardDiskAttachmentCollection **attachments);
     495    STDMETHOD(COMGETTER(HardDisk2Attachments))(ComSafeArrayOut (IHardDisk2Attachment *, aAttachments));
    500496    STDMETHOD(COMGETTER(VRDPServer))(IVRDPServer **vrdpServer);
    501497    STDMETHOD(COMGETTER(DVDDrive))(IDVDDrive **dvdDrive);
     
    526522    STDMETHOD(SetBootOrder)(ULONG aPosition, DeviceType_T aDevice);
    527523    STDMETHOD(GetBootOrder)(ULONG aPosition, DeviceType_T *aDevice);
    528     STDMETHOD(AttachHardDisk)(INPTR GUIDPARAM aId, StorageBus_T aBus, LONG aChannel, LONG aDevice);
    529     STDMETHOD(GetHardDisk)(StorageBus_T aBus, LONG aChannel, LONG aDevice, IHardDisk **aHardDisk);
    530     STDMETHOD(DetachHardDisk) (StorageBus_T aBus, LONG aChannel, LONG aDevice);
     524    STDMETHOD(AttachHardDisk2) (INPTR GUIDPARAM aId, StorageBus_T aBus,
     525                                LONG aChannel, LONG aDevice);
     526    STDMETHOD(GetHardDisk2) (StorageBus_T aBus, LONG aChannel, LONG aDevice,
     527                             IHardDisk2 **aHardDisk);
     528    STDMETHOD(DetachHardDisk2) (StorageBus_T aBus, LONG aChannel, LONG aDevice);
    531529    STDMETHOD(GetSerialPort) (ULONG slot, ISerialPort **port);
    532530    STDMETHOD(GetParallelPort) (ULONG slot, IParallelPort **port);
     
    555553    // public methods only for internal purposes
    556554
     555    InstanceType type() const { return mType; }
     556
    557557    /// @todo (dmik) add lock and make non-inlined after revising classes
    558558    //  that use it. Note: they should enter Machine lock to keep the returned
     
    560560    bool isRegistered() { return !!mData->mRegistered; }
    561561
    562     /**
    563      *  Returns the VirtualBox object this machine belongs to.
    564      *
    565      *  @note This method doesn't check this object's readiness as it is
    566      *  intended to be used only by Machine children where it is guaranteed
    567      *  that this object still exists in memory.
     562    // unsafe inline public methods for internal purposes only (ensure there is
     563    // a caller and a read lock before calling them!)
     564
     565    /**
     566     * Returns the VirtualBox object this machine belongs to.
     567     *
     568     * @note This method doesn't check this object's readiness. Intended to be
     569     * used by ready Machine children (whose readiness is bound to the parent's
     570     * one) or after doing addCaller() manually.
    568571     */
    569572    const ComObjPtr <VirtualBox, ComWeakRef> &virtualBox() const { return mParent; }
    570573
    571574    /**
    572      *  Returns this machine's name.
    573      *
    574      *  @note This method doesn't check this object's readiness as it is
    575      *  intended to be used only after adding a caller to this object (that
    576      *  guarantees that the object is ready or at least limited).
    577      */
    578     const Guid &uuid() const { return mData->mUuid; }
    579 
    580     /**
    581      *  Returns this machine's full settings file path.
    582      *
    583      *  @note This method doesn't lock this object or check its readiness as
    584      *  it is intended to be used only after adding a caller to this object
    585      *  (that guarantees that the object is ready) and locking it for reading.
     575     * Returns this machine ID.
     576     *
     577     * @note This method doesn't check this object's readiness. Intended to be
     578     * used by ready Machine children (whose readiness is bound to the parent's
     579     * one) or after adding a caller manually.
     580     */
     581    const Guid &id() const { return mData->mUuid; }
     582
     583    /**
     584     * Returns the snapshot ID this machine represents or an empty UUID if this
     585     * instance is not SnapshotMachine.
     586     *
     587     * @note This method doesn't check this object's readiness. Intended to be
     588     * used by ready Machine children (whose readiness is bound to the parent's
     589     * one) or after adding a caller manually.
     590     */
     591    inline const Guid &snapshotId() const;
     592
     593    /**
     594     * Returns this machine's full settings file path.
     595     *
     596     * @note This method doesn't lock this object or check its readiness.
     597     * Intended to be used only after doing addCaller() manually and locking it
     598     * for reading.
    586599     */
    587600    const Bstr &settingsFileFull() const { return mData->mConfigFileFull; }
    588601
    589602    /**
    590      *  Returns this machine's name.
    591      *
    592      *  @note This method doesn't lock this object or check its readiness as
    593      *  it is intended to be used only after adding a caller to this object
    594      *  (that guarantees that the object is ready) and locking it for reading.
     603     * Returns this machine name.
     604     *
     605     * @note This method doesn't lock this object or check its readiness.
     606     * Intended to be used only after doing addCaller() manually and locking it
     607     * for reading.
    595608     */
    596609    const Bstr &name() const { return mUserData->mName; }
     
    613626
    614627    void getLogFolder (Utf8Str &aLogFolder);
    615 
    616     bool isDVDImageUsed (const Guid &aId, ResourceUsage_T aUsage);
    617     bool isFloppyImageUsed (const Guid &aId, ResourceUsage_T aUsage);
    618628
    619629    HRESULT openSession (IInternalSessionControl *aControl);
     
    658668protected:
    659669
    660     enum InstanceType { IsMachine, IsSessionMachine, IsSnapshotMachine };
    661 
    662670    HRESULT registeredInit();
    663671
     
    669677    void uninitDataAndChildObjects();
    670678
    671     void ensureNoStateDependencies (AutoWriteLock &aLock);
     679    void ensureNoStateDependencies();
    672680
    673681    virtual HRESULT setMachineState (MachineState_T aMachineState);
     
    693701                          bool aSetError = false);
    694702
    695     HRESULT findHardDiskAttachment (const ComObjPtr <HardDisk> &aHd,
    696                                     ComObjPtr <Machine> *aMachine,
    697                                     ComObjPtr <Snapshot> *aSnapshot,
    698                                     ComObjPtr <HardDiskAttachment> *aHda);
    699 
    700     HRESULT prepareSaveSettings (bool &aRenamed, bool &aNew);
    701     HRESULT saveSettings (bool aMarkCurStateAsModified = true,
    702                           bool aInformCallbacksAnyway = false);
    703 
    704703    enum
    705704    {
    706         // ops for #saveSnapshotSettings()
     705        /* flags for #saveSettings() */
     706        SaveS_ResetCurStateModified = 0x01,
     707        SaveS_InformCallbacksAnyway = 0x02,
     708        /* ops for #saveSnapshotSettings() */
    707709        SaveSS_NoOp = 0x00, SaveSS_AddOp = 0x01,
    708710        SaveSS_UpdateAttrsOp = 0x02, SaveSS_UpdateAllOp = 0x03,
    709711        SaveSS_OpMask = 0xF,
    710         // flags for #saveSnapshotSettings()
    711         SaveSS_UpdateCurStateModified = 0x40,
    712         SaveSS_UpdateCurrentId = 0x80,
    713         // flags for #saveStateSettings()
     712        /* flags for #saveSnapshotSettings() */
     713        SaveSS_CurStateModified = 0x40,
     714        SaveSS_CurrentId = 0x80,
     715        /* flags for #saveStateSettings() */
    714716        SaveSTS_CurStateModified = 0x20,
    715717        SaveSTS_StateFilePath = 0x40,
     
    717719    };
    718720
     721    HRESULT prepareSaveSettings (bool &aRenamed, bool &aNew);
     722    HRESULT saveSettings (int aFlags = 0);
     723
    719724    HRESULT saveSnapshotSettings (Snapshot *aSnapshot, int aOpFlags);
    720725    HRESULT saveSnapshotSettingsWorker (settings::Key &aMachineNode,
     
    727732    HRESULT saveStateSettings (int aFlags);
    728733
    729     HRESULT wipeOutImmutableDiffs();
    730 
    731     HRESULT fixupHardDisks (bool aCommit);
    732 
    733     HRESULT createSnapshotDiffs (const Guid *aSnapshotId,
    734                                  const Bstr &aFolder,
    735                                  const ComObjPtr <Progress> &aProgress,
     734    HRESULT createImplicitDiffs (const Bstr &aFolder,
     735                                 ComObjPtr <Progress> &aProgress,
    736736                                 bool aOnline);
    737     HRESULT deleteSnapshotDiffs (const ComObjPtr <Snapshot> &aSnapshot);
     737    HRESULT deleteImplicitDiffs();
     738
     739    void fixupHardDisks2 (bool aCommit, bool aOnline = false);
    738740
    739741    HRESULT lockConfig();
     
    751753    bool isReallyModified (bool aIgnoreUserData = false);
    752754    void rollback (bool aNotify);
    753     HRESULT commit();
     755    void commit();
    754756    void copyFrom (Machine *aThat);
    755757
     
    905907    };
    906908
    907     struct Uninit {
     909    struct Uninit
     910    {
    908911        enum Reason { Unexpected, Abnormal, Normal };
    909912    };
     
    10041007    HRESULT onSnapshotChange (Snapshot *aSnapshot);
    10051008
     1009    // unsafe inline public methods for internal purposes only (ensure there is
     1010    // a caller and a read lock before calling them!)
     1011
     1012    const Guid &snapshotId() const { return mSnapshotId; }
     1013
    10061014private:
    10071015
     
    10101018    friend class Snapshot;
    10111019};
     1020
     1021// third party methods that depend on SnapshotMachine definiton
     1022
     1023inline const Guid &Machine::snapshotId() const
     1024{
     1025    return mType != IsSnapshotMachine ? Guid::Empty :
     1026                    static_cast <const SnapshotMachine *> (this)->snapshotId();
     1027}
    10121028
    10131029////////////////////////////////////////////////////////////////////////////////
     
    10281044}
    10291045
    1030 COM_DECL_READONLY_ENUM_AND_COLLECTION (Machine)
    1031 
    10321046#endif // ____H_MACHINEIMPL
  • trunk/src/VBox/Main/include/ProgressImpl.h

    r8155 r13580  
     1/* $Id$ */
    12/** @file
    23 *
     
    56
    67/*
    7  * Copyright (C) 2006-2007 Sun Microsystems, Inc.
     8 * Copyright (C) 2006-2008 Sun Microsystems, Inc.
    89 *
    910 * This file is part of VirtualBox Open Source Edition (OSE), as
     
    2627#include "Collection.h"
    2728
     29#include <VBox/com/SupportErrorInfo.h>
     30
    2831#include <iprt/semaphore.h>
    2932
     
    3437////////////////////////////////////////////////////////////////////////////////
    3538
     39/**
     40 * Base component class for progress objects.
     41 */
    3642class ATL_NO_VTABLE ProgressBase :
    37     public VirtualBoxSupportErrorInfoImpl <ProgressBase, IProgress>,
     43    public VirtualBoxBaseNEXT,
     44    public com::SupportErrorInfoBase,
    3845    public VirtualBoxSupportTranslation <ProgressBase>,
    39     public VirtualBoxBase,
    4046    public IProgress
    4147{
    4248protected:
    4349
    44     BEGIN_COM_MAP(ProgressBase)
    45         COM_INTERFACE_ENTRY(ISupportErrorInfo)
    46         COM_INTERFACE_ENTRY(IProgress)
    47     END_COM_MAP()
     50    VIRTUALBOXBASE_ADD_ERRORINFO_SUPPORT (ProgressBase)
     51
     52    DECLARE_EMPTY_CTOR_DTOR (ProgressBase)
    4853
    4954    HRESULT FinalConstruct();
    5055
    51     // public initializer/uninitializer for internal purposes only
    52     HRESULT protectedInit (
     56    // protected initializer/uninitializer for internal purposes only
     57    HRESULT protectedInit (AutoInitSpan &aAutoInitSpan,
    5358#if !defined (VBOX_COM_INPROC)
    5459                  VirtualBox *aParent,
     
    5661                  IUnknown *aInitiator,
    5762                  const BSTR aDescription, GUIDPARAMOUT aId = NULL);
    58     HRESULT protectedInit();
    59     void protectedUninit (AutoWriteLock &alock);
     63    HRESULT protectedInit (AutoInitSpan &aAutoInitSpan);
     64    void protectedUninit (AutoUninitSpan &aAutoUninitSpan);
    6065
    6166public:
     
    8085    // public methods only for internal purposes
    8186
    82     Guid id() { AutoWriteLock alock (this); return mId; }
    83     BOOL completed() { AutoWriteLock alock (this); return mCompleted; }
    84     HRESULT resultCode() { AutoWriteLock alock (this); return mResultCode; }
    85 
    86     // for VirtualBoxSupportErrorInfoImpl
    87     static const wchar_t *getComponentName() { return L"Progress"; }
     87    static HRESULT setErrorInfoOnThread (IProgress *aProgress);
     88
     89    // unsafe inline public methods for internal purposes only (ensure there is
     90    // a caller and a read lock before calling them!)
     91
     92    BOOL completed() const { return mCompleted; }
     93    HRESULT resultCode() const { return mResultCode; }
    8894
    8995protected:
    9096
    9197#if !defined (VBOX_COM_INPROC)
    92     /** weak parent */
    93     ComObjPtr <VirtualBox, ComWeakRef> mParent;
    94 #endif
    95     ComPtr <IUnknown> mInitiator;
    96 
    97     Guid mId;
    98     Bstr mDescription;
    99 
    100     // the fields below are to be initalized by subclasses
     98    /** Weak parent. */
     99    const ComObjPtr <VirtualBox, ComWeakRef> mParent;
     100#endif
     101
     102    const ComPtr <IUnknown> mInitiator;
     103
     104    const Guid mId;
     105    const Bstr mDescription;
     106
     107    /* The fields below are to be properly initalized by subclasses */
    101108
    102109    BOOL mCompleted;
     
    114121////////////////////////////////////////////////////////////////////////////////
    115122
     123/**
     124 * Normal progress object.
     125 */
    116126class ATL_NO_VTABLE Progress :
    117     public VirtualBoxSupportTranslation <Progress>,
    118     public ProgressBase
     127    public com::SupportErrorInfoDerived <ProgressBase, Progress, IProgress>,
     128    public VirtualBoxSupportTranslation <Progress>
    119129{
    120130
    121131public:
    122132
    123     VIRTUALBOXSUPPORTTRANSLATION_OVERRIDE(Progress)
    124 
    125     DECLARE_NOT_AGGREGATABLE(Progress)
     133    VIRTUALBOXSUPPORTTRANSLATION_OVERRIDE (Progress)
     134
     135    DECLARE_NOT_AGGREGATABLE (Progress)
    126136
    127137    DECLARE_PROTECT_FINAL_CONSTRUCT()
    128138
    129     BEGIN_COM_MAP(Progress)
    130         COM_INTERFACE_ENTRY(ISupportErrorInfo)
    131         COM_INTERFACE_ENTRY(IProgress)
     139    BEGIN_COM_MAP (Progress)
     140        COM_INTERFACE_ENTRY (ISupportErrorInfo)
     141        COM_INTERFACE_ENTRY (IProgress)
    132142    END_COM_MAP()
    133143
     
    185195                                const Bstr &aComponent, const Bstr &aText);
    186196
     197    /** For com::SupportErrorInfoImpl. */
     198    static const char *ComponentName() { return "Progress"; }
     199
    187200private:
    188201
     
    194207
    195208/**
    196  *  The CombinedProgress class allows to combine several progress objects
    197  *  to a single progress component. This single progress component will treat
    198  *  all operations of individual progress objects as a single sequence of
    199  *  operations, that follow each other in the same order as progress objects are
    200  *  passed to the #init() method.
    201  *
    202  *  Individual progress objects are sequentially combined so that this progress
    203  *  object:
     209 * The CombinedProgress class allows to combine several progress objects to a
     210 * single progress component. This single progress component will treat all
     211 * operations of individual progress objects as a single sequence of operations
     212 * that follow each other in the same order as progress objects are passed to
     213 * the #init() method.
     214 *
     215 * Individual progress objects are sequentially combined so that this progress
     216 * object:
    204217 *
    205218 *  -   is cancelable only if all progresses are cancelable.
     
    222235 *      progress, normalized to 100%.
    223236 *
    224  *  @note
    225  *      It's the respoisibility of the combined progress object creator
    226  *      to complete individual progresses in the right order: if, let's say,
    227  *      the last progress is completed before all previous ones,
    228  *      #WaitForCompletion(-1) will most likely give 100% CPU load because it
    229  *      will be in a loop calling a method that returns immediately.
     237 * @note It's the respoisibility of the combined progress object creator to
     238 *       complete individual progresses in the right order: if, let's say, the
     239 *       last progress is completed before all previous ones,
     240 *       #WaitForCompletion(-1) will most likely give 100% CPU load because it
     241 *       will be in a loop calling a method that returns immediately.
    230242 */
    231243class ATL_NO_VTABLE CombinedProgress :
    232     public VirtualBoxSupportTranslation <CombinedProgress>,
    233     public ProgressBase
     244    public com::SupportErrorInfoDerived <ProgressBase, CombinedProgress, IProgress>,
     245    public VirtualBoxSupportTranslation <CombinedProgress>
    234246{
    235247
    236248public:
    237249
    238     VIRTUALBOXSUPPORTTRANSLATION_OVERRIDE(CombinedProgress)
    239 
    240     DECLARE_NOT_AGGREGATABLE(CombinedProgress)
     250    VIRTUALBOXSUPPORTTRANSLATION_OVERRIDE (CombinedProgress)
     251
     252    DECLARE_NOT_AGGREGATABLE (CombinedProgress)
    241253
    242254    DECLARE_PROTECT_FINAL_CONSTRUCT()
    243255
    244     BEGIN_COM_MAP(CombinedProgress)
    245         COM_INTERFACE_ENTRY(ISupportErrorInfo)
    246         COM_INTERFACE_ENTRY(IProgress)
     256    BEGIN_COM_MAP (CombinedProgress)
     257        COM_INTERFACE_ENTRY (ISupportErrorInfo)
     258        COM_INTERFACE_ENTRY (IProgress)
    247259    END_COM_MAP()
    248260
     
    261273                  const BSTR aDescription,
    262274                  IProgress *aProgress1, IProgress *aProgress2,
    263                   GUIDPARAMOUT aId = NULL)
    264     {
    265         AutoWriteLock alock (this);
    266         ComAssertRet (!isReady(), E_UNEXPECTED);
    267 
    268         mProgresses.resize (2);
    269         mProgresses [0] = aProgress1;
    270         mProgresses [1] = aProgress2;
    271 
    272         return protectedInit (
    273 #if !defined (VBOX_COM_INPROC)
    274                               aParent,
    275 #endif
    276                               aInitiator, aDescription, aId);
    277     }
    278 
     275                  GUIDPARAMOUT aId = NULL);
     276
     277    /**
     278     * Initializes the combined progress object given the first and the last
     279     * normal progress object from the list.
     280     *
     281     * @param aParent       See ProgressBase::init().
     282     * @param aInitiator    See ProgressBase::init().
     283     * @param aDescription  See ProgressBase::init().
     284     * @param aFirstProgress Iterator of the first normal progress object.
     285     * @param aSecondProgress Iterator of the last normal progress object.
     286     * @param aId           See ProgressBase::init().
     287     */
    279288    template <typename InputIterator>
    280289    HRESULT init (
     
    287296                  GUIDPARAMOUT aId = NULL)
    288297    {
    289         AutoWriteLock alock (this);
    290         ComAssertRet (!isReady(), E_UNEXPECTED);
     298        /* Enclose the state transition NotReady->InInit->Ready */
     299        AutoInitSpan autoInitSpan (this);
     300        AssertReturn (autoInitSpan.isOk(), E_UNEXPECTED);
    291301
    292302        mProgresses = ProgressVector (aFirstProgress, aLastProgress);
    293303
    294         return protectedInit (
    295 #if !defined (VBOX_COM_INPROC)
    296                               aParent,
    297 #endif
    298                               aInitiator, aDescription, aId);
     304        HRESULT rc = protectedInit (autoInitSpan,
     305#if !defined (VBOX_COM_INPROC)
     306                                    aParent,
     307#endif
     308                                    aInitiator, aDescription, aId);
     309
     310        /* Confirm a successful initialization when it's the case */
     311        if (SUCCEEDED (rc))
     312            autoInitSpan.setSucceeded();
     313
     314        return rc;
    299315    }
    300316
    301317protected:
    302318
    303     HRESULT protectedInit (
     319    HRESULT protectedInit (AutoInitSpan &aAutoInitSpan,
    304320#if !defined (VBOX_COM_INPROC)
    305321                           VirtualBox *aParent,
     
    329345    // public methods only for internal purposes
    330346
     347    /** For com::SupportErrorInfoImpl. */
     348    static const char *ComponentName() { return "CombinedProgress"; }
     349
    331350private:
    332351
     
    342361COM_DECL_READONLY_ENUM_AND_COLLECTION_AS (Progress, IProgress)
    343362
    344 #endif // ____H_PROGRESSIMPL
     363#endif /* ____H_PROGRESSIMPL */
  • trunk/src/VBox/Main/include/SnapshotImpl.h

    r8155 r13580  
    113113    ComObjPtr <Snapshot> findChildOrSelf (INPTR BSTR aName);
    114114
    115     bool isDVDImageUsed (const Guid &aId);
    116     bool isFloppyImageUsed (const Guid &aId);
    117 
    118115    void updateSavedStatePaths (const char *aOldPath, const char *aNewPath);
    119116
  • trunk/src/VBox/Main/include/SystemPropertiesImpl.h

    r8155 r13580  
    2626
    2727#include "VirtualBoxBase.h"
     28#include "HardDiskFormatImpl.h"
     29
     30#include <VBox/com/array.h>
     31
     32#include <list>
    2833
    2934class VirtualBox;
     
    6671    STDMETHOD(COMGETTER(ParallelPortCount) (ULONG *count));
    6772    STDMETHOD(COMGETTER(MaxBootPosition) (ULONG *aMaxBootPosition));
    68     STDMETHOD(COMGETTER(DefaultVDIFolder)) (BSTR *aDefaultVDIFolder);
    69     STDMETHOD(COMSETTER(DefaultVDIFolder)) (INPTR BSTR aDefaultVDIFolder);
    7073    STDMETHOD(COMGETTER(DefaultMachineFolder)) (BSTR *aDefaultMachineFolder);
    7174    STDMETHOD(COMSETTER(DefaultMachineFolder)) (INPTR BSTR aDefaultMachineFolder);
     75    STDMETHOD(COMGETTER(DefaultHardDiskFolder)) (BSTR *aDefaultHardDiskFolder);
     76    STDMETHOD(COMSETTER(DefaultHardDiskFolder)) (INPTR BSTR aDefaultHardDiskFolder);
     77    STDMETHOD(COMGETTER(HardDiskFormats)) (ComSafeArrayOut (IHardDiskFormat *, aHardDiskFormats));
    7278    STDMETHOD(COMGETTER(RemoteDisplayAuthLibrary)) (BSTR *aRemoteDisplayAuthLibrary);
    7379    STDMETHOD(COMSETTER(RemoteDisplayAuthLibrary)) (INPTR BSTR aRemoteDisplayAuthLibrary);
     
    8490    HRESULT saveSettings (settings::Key &aGlobal);
    8591
    86     /** Default VDI path (as is, not full). Not thread safe (use object lock). */
    87     const Bstr &defaultVDIFolder() { return mDefaultVDIFolder; }
    88     /** Default Machine path (full). Not thread safe (use object lock). */
    89     const Bstr &defaultVDIFolderFull() { return mDefaultVDIFolderFull; }
    9092    /** Default Machine path (as is, not full). Not thread safe (use object lock). */
    9193    const Bstr &defaultMachineFolder() { return mDefaultMachineFolder; }
    9294    /** Default Machine path (full). Not thread safe (use object lock). */
    9395    const Bstr &defaultMachineFolderFull() { return mDefaultMachineFolderFull; }
     96    /** Default hard disk path (as is, not full). Not thread safe (use object lock). */
     97    const Bstr &defaultHardDiskFolder() { return mDefaultHardDiskFolder; }
     98    /** Default hard disk path (full). Not thread safe (use object lock). */
     99    const Bstr &defaultHardDiskFolderFull() { return mDefaultHardDiskFolderFull; }
    94100
    95101    // for VirtualBoxSupportErrorInfoImpl
     
    98104private:
    99105
    100     HRESULT setDefaultVDIFolder (const BSTR aPath);
     106    typedef std::list <ComObjPtr <HardDiskFormat> > HardDiskFormatList;
     107
    101108    HRESULT setDefaultMachineFolder (const BSTR aPath);
     109    HRESULT setDefaultHardDiskFolder (const BSTR aPath);
    102110    HRESULT setRemoteDisplayAuthLibrary (const BSTR aPath);
    103111    HRESULT setWebServiceAuthLibrary (const BSTR aPath);
     
    105113    ComObjPtr <VirtualBox, ComWeakRef> mParent;
    106114
    107     Bstr mDefaultVDIFolder;
    108     Bstr mDefaultVDIFolderFull;
    109115    Bstr mDefaultMachineFolder;
    110116    Bstr mDefaultMachineFolderFull;
     117    Bstr mDefaultHardDiskFolder;
     118    Bstr mDefaultHardDiskFolderFull;
     119
     120    HardDiskFormatList mHardDiskFormats;
     121
    111122    Bstr mRemoteDisplayAuthLibrary;
    112123    Bstr mWebServiceAuthLibrary;
  • trunk/src/VBox/Main/include/VirtualBoxBase.h

    r8744 r13580  
    4848#include <atlcom.h>
    4949
    50 // use a special version of the singleton class factory,
    51 //  see KB811591 in msdn for more info.
     50/* use a special version of the singleton class factory,
     51 * see KB811591 in msdn for more info. */
    5252
    5353#undef DECLARE_CLASSFACTORY_SINGLETON
     
    120120};
    121121
    122 #endif // !defined (VBOX_WITH_XPCOM)
     122#endif /* !defined (VBOX_WITH_XPCOM) */
    123123
    124124// macros
     
    434434////////////////////////////////////////////////////////////////////////////////
    435435
    436 class ATL_NO_VTABLE VirtualBoxBaseNEXT_base
    437 #if !defined (VBOX_WITH_XPCOM)
    438     : public CComObjectRootEx <CComMultiThreadModel>
    439 #else
    440     : public CComObjectRootEx
    441 #endif
    442     , public Lockable
     436/**
     437 * Abstract base class for all component classes implementing COM
     438 * interfaces of the VirtualBox COM library.
     439 *
     440 * Declares functionality that should be available in all components.
     441 *
     442 * Note that this class is always subclassed using the virtual keyword so
     443 * that only one instance of its VTBL and data is present in each derived class
     444 * even in case if VirtualBoxBaseProto appears more than once among base classes
     445 * of the particular component as a result of multiple inheritance.
     446 *
     447 * This makes it possible to have intermediate base classes used by several
     448 * components that implement some common interface fuctionality but still let
     449 * the final component classe choose what VirtualBoxBase variant it wants to
     450 * use.
     451 *
     452 * Among the basic functionality implemented by this class is the primary object
     453 * state that indicates if the object is ready to serve the calls, and if not,
     454 * what stage it is currently at. Here is the pirmary state diagram:
     455 *
     456 *              +-------------------------------------------------------+
     457 *              |                                                       |
     458 *              |         (InitFailed) -----------------------+         |
     459 *              |              ^                              |         |
     460 *              v              |                              v         |
     461 *  [*] ---> NotReady ----> (InInit) -----> Ready -----> (InUninit) ----+
     462 *                     ^       |      ^       |               ^
     463 *                     |       v      |       v               |
     464 *                     |    Limited   |  (MayUninit) --> (WillUninit)
     465 *                     |       |      |       |
     466 *                     +-------+      +-------+
     467 *
     468 * The object is fully operational only when its state is Ready. The Limited
     469 * state means that only some vital part of the object is operational, and it
     470 * requires some sort of reinitialization to become fully operational. The
     471 * NotReady state means the object is basically dead: it either was not yet
     472 * initialized after creation at all, or was uninitialized and is waiting to be
     473 * destroyed when the last reference to it is released. All other states are
     474 * transitional.
     475 *
     476 * The NotReady->InInit->Ready, NotReady->InInit->Limited and
     477 * NotReady->InInit->InitFailed transition is done by the AutoInitSpan smart
     478 * class.
     479 *
     480 * The Limited->InInit->Ready, Limited->InInit->Limited and
     481 * Limited->InInit->InitFailed transition is done by the AutoReinitSpan smart
     482 * class.
     483 *
     484 * The Ready->InUninit->NotReady, InitFailed->InUninit->NotReady and
     485 * WillUninit->InUninit->NotReady transitions are done by the AutoUninitSpan
     486 * smart class.
     487 *
     488 * The Ready->MayUninit->Ready and Ready->MayUninit->WillUninit transitions are
     489 * done by the AutoMayUninitSpan smart class.
     490 *
     491 * In order to maintain the primary state integrity and declared functionality
     492 * all subclasses must:
     493 *
     494 * 1) Use the above Auto*Span classes to perform state transitions. See the
     495 *    individual class doescriptions for details.
     496 *
     497 * 2) All public methods of subclasses (i.e. all methods that can be called
     498 *    directly, not only from within other methods of the subclass) must have a
     499 *    standard prolog as described in the AutoCaller and AutoLimitedCaller
     500 *    documentation. Alternatively, they must use addCaller()/releaseCaller()
     501 *    directly (and therefire have both the prolog and the epilog), but this is
     502 *    not recommended.
     503 */
     504class ATL_NO_VTABLE VirtualBoxBaseProto : public Lockable
    443505{
    444506public:
    445507
    446     enum State { NotReady, Ready, InInit, InUninit, InitFailed, Limited };
     508    enum State { NotReady, Ready, InInit, InUninit, InitFailed, Limited,
     509                 MayUninit, WillUninit };
    447510
    448511protected:
    449512
    450     VirtualBoxBaseNEXT_base();
    451     virtual ~VirtualBoxBaseNEXT_base();
     513    VirtualBoxBaseProto();
     514    virtual ~VirtualBoxBaseProto();
    452515
    453516public:
     
    457520
    458521    /**
    459      *  Virtual unintialization method.
    460      *  Must be called by all implementations (COM classes) when the last
    461      *  reference to the object is released, before calling the destructor.
    462      *  Also, this method is called automatically by the uninit() method of the
    463      *  parent of this object, when this object is a dependent child of a class
    464      *  derived from VirtualBoxBaseWithChildren (@sa
    465      *  VirtualBoxBaseWithChildren::addDependentChild).
     522     * Unintialization method.
     523     *
     524     * Must be called by all final implementations (component classes) when the
     525     * last reference to the object is released, before calling the destructor.
     526     *
     527     * This method is also automatically called by the uninit() method of this
     528     * object's parent if this object is a dependent child of a class derived
     529     * from VirtualBoxBaseWithChildren (see
     530     * VirtualBoxBaseWithChildren::addDependentChild).
     531     *
     532     * @note Never call this method the AutoCaller scope or after the
     533     *       #addCaller() call not paired by #releaseCaller() because it is a
     534     *       guaranteed deadlock. See AutoUninitSpan for details.
    466535     */
    467536    virtual void uninit() {}
     
    471540
    472541    /**
    473      *  Adds a limited caller. This method is equivalent to doing
    474      *  <tt>addCaller (aState, true)</tt>, but it is preferred because
    475      *  provides better self-descriptiveness. See #addCaller() for more info.
     542     * Adds a limited caller. This method is equivalent to doing
     543     * <tt>addCaller (aState, true)</tt>, but it is preferred because provides
     544     * better self-descriptiveness. See #addCaller() for more info.
    476545     */
    477546    HRESULT addLimitedCaller (State *aState = NULL)
     
    481550
    482551    /**
    483      *  Smart class that automatically increases the number of callers of the
    484      *  given VirtualBoxBase object when an instance is constructed and decreases
    485      *  it back when the created instance goes out of scope (i.e. gets destroyed).
    486      *
    487      *  If #rc() returns a failure after the instance creation, it means that
    488      *  the managed VirtualBoxBase object is not Ready, or in any other invalid
    489      *  state, so that the caller must not use the object and can return this
    490      *  failed result code to the upper level.
    491      *
    492      *  See VirtualBoxBase::addCaller(), VirtualBoxBase::addLimitedCaller() and
    493      *  VirtualBoxBase::releaseCaller() for more details about object callers.
    494      *
    495      *  @param aLimited |false| if this template should use
     552     * Smart class that automatically increases the number of callers of the
     553     * given VirtualBoxBase object when an instance is constructed and decreases
     554     * it back when the created instance goes out of scope (i.e. gets destroyed).
     555     *
     556     * If #rc() returns a failure after the instance creation, it means that
     557     * the managed VirtualBoxBase object is not Ready, or in any other invalid
     558     * state, so that the caller must not use the object and can return this
     559     * failed result code to the upper level.
     560     *
     561     * See VirtualBoxBase::addCaller(), VirtualBoxBase::addLimitedCaller() and
     562     * VirtualBoxBase::releaseCaller() for more details about object callers.
     563     *
     564     * @param aLimited |false| if this template should use
    496565     *                  VirtualiBoxBase::addCaller() calls to add callers, or
    497566     *                  |true| if VirtualiBoxBase::addLimitedCaller() should be
    498567     *                  used.
    499568     *
    500      *  @note It is preferrable to use the AutoCaller and AutoLimitedCaller
    501      *        classes than specify the @a aLimited argument, for better
    502      *        self-descriptiveness.
     569     * @note It is preferrable to use the AutoCaller and AutoLimitedCaller
     570     *       classes than specify the @a aLimited argument, for better
     571     *       self-descriptiveness.
    503572     */
    504573    template <bool aLimited>
     
    508577
    509578        /**
    510          *  Increases the number of callers of the given object
    511          *  by calling VirtualBoxBase::addCaller().
     579         * Increases the number of callers of the given object by calling
     580         * VirtualBoxBase::addCaller().
    512581         *
    513          *  @param aObj     Object to add a caller to. If NULL, this
     582         * @param aObj      Object to add a caller to. If NULL, this
    514583         *                  instance is effectively turned to no-op (where
    515584         *                  rc() will return S_OK and state() will be
    516585         *                  NotReady).
    517586         */
    518         AutoCallerBase (VirtualBoxBaseNEXT_base *aObj)
     587        AutoCallerBase (VirtualBoxBaseProto *aObj)
    519588            : mObj (aObj)
    520589            , mRC (S_OK)
     
    526595
    527596        /**
    528          *  If the number of callers was successfully increased,
    529          *  decreases it using VirtualBoxBase::releaseCaller(), otherwise
    530          *  does nothing.
     597         * If the number of callers was successfully increased, decreases it
     598         * using VirtualBoxBase::releaseCaller(), otherwise does nothing.
    531599         */
    532600        ~AutoCallerBase()
     
    537605
    538606        /**
    539          *  Stores the result code returned by VirtualBoxBase::addCaller()
    540          *  after instance creation or after the last #add() call. A successful
    541          *  result code means the number of callers was successfully increased.
     607         * Stores the result code returned by VirtualBoxBase::addCaller() after
     608         * instance creation or after the last #add() call. A successful result
     609         * code means the number of callers was successfully increased.
    542610         */
    543611        HRESULT rc() const { return mRC; }
    544612
    545613        /**
    546          *  Returns |true| if |SUCCEEDED (rc())| is |true|, for convenience.
    547          *  |true| means the number of callers was successfully increased.
     614         * Returns |true| if |SUCCEEDED (rc())| is |true|, for convenience.
     615         * |true| means the number of callers was successfully increased.
    548616         */
    549617        bool isOk() const { return SUCCEEDED (mRC); }
    550618
    551619        /**
    552          *  Stores the object state returned by VirtualBoxBase::addCaller()
    553          *  after instance creation or after the last #add() call.
     620         * Stores the object state returned by VirtualBoxBase::addCaller() after
     621         * instance creation or after the last #add() call.
    554622         */
    555623        State state() const { return mState; }
    556624
    557625        /**
    558          *  Temporarily decreases the number of callers of the managed object.
    559          *  May only be called if #isOk() returns |true|. Note that #rc() will
    560          *  return E_FAIL after this method succeeds.
     626         * Temporarily decreases the number of callers of the managed object.
     627         * May only be called if #isOk() returns |true|. Note that #rc() will
     628         * return E_FAIL after this method succeeds.
    561629         */
    562630        void release()
     
    572640
    573641        /**
    574          *  Restores the number of callers decreased by #release(). May only
    575          *  be called after #release().
     642         * Restores the number of callers decreased by #release(). May only be
     643         * called after #release().
    576644         */
    577645        void add()
     
    582650        }
    583651
     652        /**
     653         * Attaches another object to this caller instance.
     654         * The previous object's caller is released before the new one is added.
     655         *
     656         * @param aObj  New object to attach, may be @c NULL.
     657         */
     658        void attach (VirtualBoxBaseProto *aObj)
     659        {
     660            /* detect simple self-reattachment */
     661            if (mObj != aObj)
     662            {
     663                if (mObj && SUCCEEDED (mRC))
     664                    release();
     665                mObj = aObj;
     666                add();
     667            }
     668        }
     669
     670        /** Verbose equivalent to <tt>attach (NULL)</tt>. */
     671        void detach() { attach (NULL); }
     672
    584673    private:
    585674
     
    587676        DECLARE_CLS_NEW_DELETE_NOOP (AutoCallerBase)
    588677
    589         VirtualBoxBaseNEXT_base *mObj;
     678        VirtualBoxBaseProto *mObj;
    590679        HRESULT mRC;
    591680        State mState;
     
    593682
    594683    /**
    595      *  Smart class that automatically increases the number of normal
    596      *  (non-limited) callers of the given VirtualBoxBase object when an
    597      *  instance is constructed and decreases it back when the created instance
    598      *  goes out of scope (i.e. gets destroyed).
    599      *
    600      *  A typical usage pattern to declare a normal method of some object
    601      *  (i.e. a method that is valid only when the object provides its
    602      *  full functionality) is:
    603      *  <code>
    604      *  STDMETHODIMP Component::Foo()
    605      *  {
    606      *      AutoCaller autoCaller (this);
    607      *      CheckComRCReturnRC (autoCaller.rc());
    608      *      ...
    609      *  </code>
    610      *
    611      *  Using this class is equivalent to using the AutoCallerBase template
    612      *  with the @a aLimited argument set to |false|, but this class is
    613      *  preferred because provides better self-descriptiveness.
    614      *
    615      *  See AutoCallerBase for more information about auto caller functionality.
     684     * Smart class that automatically increases the number of normal
     685     * (non-limited) callers of the given VirtualBoxBase object when an instance
     686     * is constructed and decreases it back when the created instance goes out
     687     * of scope (i.e. gets destroyed).
     688     *
     689     * A typical usage pattern to declare a normal method of some object (i.e. a
     690     * method that is valid only when the object provides its full
     691     * functionality) is:
     692     * <code>
     693     * STDMETHODIMP Component::Foo()
     694     * {
     695     *     AutoCaller autoCaller (this);
     696     *     CheckComRCReturnRC (autoCaller.rc());
     697     *     ...
     698     * </code>
     699     *
     700     * Using this class is equivalent to using the AutoCallerBase template with
     701     * the @a aLimited argument set to |false|, but this class is preferred
     702     * because provides better self-descriptiveness.
     703     *
     704     * See AutoCallerBase for more information about auto caller functionality.
    616705     */
    617706    typedef AutoCallerBase <false> AutoCaller;
    618707
    619708    /**
    620      *  Smart class that automatically increases the number of limited callers
    621      *  of the given VirtualBoxBase object when an instance is constructed and
    622      *  decreases it back when the created instance goes out of scope (i.e.
    623      *  gets destroyed).
    624      *
    625      *  A typical usage pattern to declare a limited method of some object
    626      *  (i.e. a method that is valid even if the object doesn't provide its
    627      *  full functionality) is:
    628      *  <code>
    629      *  STDMETHODIMP Component::Bar()
    630      *  {
    631      *      AutoLimitedCaller autoCaller (this);
    632      *      CheckComRCReturnRC (autoCaller.rc());
    633      *      ...
    634      *  </code>
    635      *
    636      *  Using this class is equivalent to using the AutoCallerBase template
    637      *  with the @a aLimited argument set to |true|, but this class is
    638      *  preferred because provides better self-descriptiveness.
    639      *
    640      *  See AutoCallerBase for more information about auto caller functionality.
     709     * Smart class that automatically increases the number of limited callers of
     710     * the given VirtualBoxBase object when an instance is constructed and
     711     * decreases it back when the created instance goes out of scope (i.e. gets
     712     * destroyed).
     713     *
     714     * A typical usage pattern to declare a limited method of some object (i.e.
     715     * a method that is valid even if the object doesn't provide its full
     716     * functionality) is:
     717     * <code>
     718     * STDMETHODIMP Component::Bar()
     719     * {
     720     *     AutoLimitedCaller autoCaller (this);
     721     *     CheckComRCReturnRC (autoCaller.rc());
     722     *     ...
     723     * </code>
     724     *
     725     * Using this class is equivalent to using the AutoCallerBase template with
     726     * the @a aLimited argument set to |true|, but this class is preferred
     727     * because provides better self-descriptiveness.
     728     *
     729     * See AutoCallerBase for more information about auto caller functionality.
    641730     */
    642731    typedef AutoCallerBase <true> AutoLimitedCaller;
     
    645734
    646735    /**
    647      *  Smart class to enclose the state transition NotReady->InInit->Ready.
    648      *
    649      *  Instances must be created at the beginning of init() methods of
    650      *  VirtualBoxBase subclasses as a stack-based variable using |this| pointer
    651      *  as the argument. When this variable is created it automatically places
    652      *  the object to the InInit state.
    653      *
    654      *  When the created variable goes out of scope (i.e. gets destroyed),
    655      *  depending on the success status of this initialization span, it either
    656      *  places the object to the Ready state or calls the object's
    657      *  VirtualBoxBase::uninit() method which is supposed to place the object
    658      *  back to the NotReady state using the AutoUninitSpan class.
    659      *
    660      *  The initial success status of the initialization span is determined by
    661      *  the @a aSuccess argument of the AutoInitSpan constructor (|false| by
    662      *  default). Inside the initialization span, the success status can be set
    663      *  to |true| using #setSucceeded() or to |false| using #setFailed(). Please
    664      *  don't forget to set the correct success status before letting the
    665      *  AutoInitSpan variable go out of scope (for example, by performing an
    666      *  early return from the init() method)!
    667      *
    668      *  Note that if an instance of this class gets constructed when the
    669      *  object is in the state other than NotReady, #isOk() returns |false| and
    670      *  methods of this class do nothing: the state transition is not performed.
    671      *
    672      *  A typical usage pattern is:
    673      *  <code>
    674      *  HRESULT Component::init()
    675      *  {
    676      *      AutoInitSpan autoInitSpan (this);
    677      *      AssertReturn (autoInitSpan.isOk(), E_UNEXPECTED);
    678      *      ...
    679      *      if (FAILED (rc))
    680      *          return rc;
    681      *      ...
    682      *      if (SUCCEEDED (rc))
    683      *          autoInitSpan.setSucceeded();
    684      *      return rc;
    685      *  }
    686      *  </code>
    687      *
    688      *  @note Never create instances of this class outside init() methods of
    689      *  VirtualBoxBase subclasses and never pass anything other than |this| as
    690      *  the argument to the constructor!
     736     * Smart class to enclose the state transition NotReady->InInit->Ready.
     737     *
     738     * The purpose of this span is to protect object initialization.
     739     *
     740     * Instances must be created as a stack-based variable taking |this| pointer
     741     * as the argument at the beginning of init() methods of VirtualBoxBase
     742     * subclasses. When this variable is created it automatically places the
     743     * object to the InInit state.
     744     *
     745     * When the created variable goes out of scope (i.e. gets destroyed) then,
     746     * depending on the result status of this initialization span, it either
     747     * places the object to Ready or Limited state or calls the object's
     748     * VirtualBoxBase::uninit() method which is supposed to place the object
     749     * back to the NotReady state using the AutoUninitSpan class.
     750     *
     751     * The initial result status of the initialization span is determined by the
     752     * @a aResult argument of the AutoInitSpan constructor (Result::Failed by
     753     * default). Inside the initialization span, the success status can be set
     754     * to Result::Succeeded using #setSucceeded(), to to Result::Limited using
     755     * #setLimited() or to Result::Failed using #setFailed(). Please don't
     756     * forget to set the correct success status before getting the AutoInitSpan
     757     * variable destryed (for example, by performing an early return from
     758     * the init() method)!
     759     *
     760     * Note that if an instance of this class gets constructed when the object
     761     * is in the state other than NotReady, #isOk() returns |false| and methods
     762     * of this class do nothing: the state transition is not performed.
     763     *
     764     * A typical usage pattern is:
     765     * <code>
     766     * HRESULT Component::init()
     767     * {
     768     *     AutoInitSpan autoInitSpan (this);
     769     *     AssertReturn (autoInitSpan.isOk(), E_UNEXPECTED);
     770     *     ...
     771     *     if (FAILED (rc))
     772     *         return rc;
     773     *     ...
     774     *     if (SUCCEEDED (rc))
     775     *         autoInitSpan.setSucceeded();
     776     *     return rc;
     777     * }
     778     * </code>
     779     *
     780     * @note Never create instances of this class outside init() methods of
     781     *       VirtualBoxBase subclasses and never pass anything other than |this|
     782     *       as the argument to the constructor!
    691783     */
    692784    class AutoInitSpan
     
    694786    public:
    695787
    696         enum Status { Failed = 0x0, Succeeded = 0x1, Limited = 0x2 };
    697 
    698         AutoInitSpan (VirtualBoxBaseNEXT_base *aObj, Status aStatus = Failed);
     788        enum Result { Failed = 0x0, Succeeded = 0x1, Limited = 0x2 };
     789
     790        AutoInitSpan (VirtualBoxBaseProto *aObj, Result aResult = Failed);
    699791        ~AutoInitSpan();
    700792
    701793        /**
    702          *  Returns |true| if this instance has been created at the right moment
    703          *  (when the object was in the NotReady state) and |false| otherwise.
     794         * Returns |true| if this instance has been created at the right moment
     795         * (when the object was in the NotReady state) and |false| otherwise.
    704796         */
    705797        bool isOk() const { return mOk; }
    706798
    707799        /**
    708          *  Sets the initialization status to Succeeded to indicates successful
    709          *  initialization. The AutoInitSpan destructor will place the managed
    710          *  VirtualBoxBase object to the Ready state.
     800         * Sets the initialization status to Succeeded to indicates successful
     801         * initialization. The AutoInitSpan destructor will place the managed
     802         * VirtualBoxBase object to the Ready state.
    711803         */
    712         void setSucceeded() { mStatus = Succeeded; }
     804        void setSucceeded() { mResult = Succeeded; }
    713805
    714806        /**
    715          *  Sets the initialization status to Succeeded to indicate limited
    716          *  (partly successful) initialization. The AutoInitSpan destructor will
    717          *  place the managed VirtualBoxBase object to the Limited state.
     807         * Sets the initialization status to Succeeded to indicate limited
     808         * (partly successful) initialization. The AutoInitSpan destructor will
     809         * place the managed VirtualBoxBase object to the Limited state.
    718810         */
    719         void setLimited() { mStatus = Limited; }
     811        void setLimited() { mResult = Limited; }
    720812
    721813        /**
    722          *  Sets the initialization status to Failure to indicates failed
    723          *  initialization. The AutoInitSpan destructor will place the managed
    724          *  VirtualBoxBase object to the InitFailed state and will automatically
    725          *  call its uninit() method which is supposed to place the object back
    726          *  to the NotReady state using AutoUninitSpan.
     814         * Sets the initialization status to Failure to indicates failed
     815         * initialization. The AutoInitSpan destructor will place the managed
     816         * VirtualBoxBase object to the InitFailed state and will automatically
     817         * call its uninit() method which is supposed to place the object back
     818         * to the NotReady state using AutoUninitSpan.
    727819         */
    728         void setFailed() { mStatus = Failed; }
    729 
    730         /** Returns the current initialization status. */
    731         Status status() { return mStatus; }
     820        void setFailed() { mResult = Failed; }
     821
     822        /** Returns the current initialization result. */
     823        Result result() { return mResult; }
    732824
    733825    private:
     
    736828        DECLARE_CLS_NEW_DELETE_NOOP (AutoInitSpan)
    737829
    738         VirtualBoxBaseNEXT_base *mObj;
    739         Status mStatus : 3; // must be at least total number of bits + 1 (sign)
     830        VirtualBoxBaseProto *mObj;
     831        Result mResult : 3; // must be at least total number of bits + 1 (sign)
    740832        bool mOk : 1;
    741833    };
    742834
    743835    /**
    744      *  Smart class to enclose the state transition Limited->InInit->Ready.
    745      *
    746      *  Instances must be created at the beginning of methods of VirtualBoxBase
    747      *  subclasses that try to re-initialize the object to bring it to the
    748      *  Ready state (full functionality) after partial initialization
    749      *  (limited functionality)>, as a stack-based variable using |this| pointer
    750      *  as the argument. When this variable is created it automatically places
    751      *  the object to the InInit state.
    752      *
    753      *  When the created variable goes out of scope (i.e. gets destroyed),
    754      *  depending on the success status of this initialization span, it either
    755      *  places the object to the Ready state or brings it back to the Limited
    756      *  state.
    757      *
    758      *  The initial success status of the re-initialization span is |false|.
    759      *  In order to make it successful, #setSucceeded() must be called before
    760      *  the instance is destroyed.
    761      *
    762      *  Note that if an instance of this class gets constructed when the
    763      *  object is in the state other than Limited, #isOk() returns |false| and
    764      *  methods of this class do nothing: the state transition is not performed.
    765      *
    766      *  A typical usage pattern is:
    767      *  <code>
    768      *  HRESULT Component::reinit()
    769      *  {
    770      *      AutoReadySpan autoReadySpan (this);
    771      *      AssertReturn (autoReadySpan.isOk(), E_UNEXPECTED);
    772      *      ...
    773      *      if (FAILED (rc))
    774      *          return rc;
    775      *      ...
    776      *      if (SUCCEEDED (rc))
    777      *          autoReadySpan.setSucceeded();
    778      *      return rc;
    779      *  }
    780      *  </code>
    781      *
    782      *  @note Never create instances of this class outside re-initialization
    783      *  methods of VirtualBoxBase subclasses and never pass anything other than
    784      *  |this| as the argument to the constructor!
    785      */
    786     class AutoReadySpan
     836     * Smart class to enclose the state transition Limited->InInit->Ready.
     837     *
     838     * The purpose of this span is to protect object re-initialization.
     839     *
     840     * Instances must be created as a stack-based variable taking |this| pointer
     841     * as the argument at the beginning of methods of VirtualBoxBase
     842     * subclasses that try to re-initialize the object to bring it to the Ready
     843     * state (full functionality) after partial initialization (limited
     844     * functionality). When this variable is created, it automatically places
     845     * the object to the InInit state.
     846     *
     847     * When the created variable goes out of scope (i.e. gets destroyed),
     848     * depending on the success status of this initialization span, it either
     849     * places the object to the Ready state or brings it back to the Limited
     850     * state.
     851     *
     852     * The initial success status of the re-initialization span is |false|. In
     853     * order to make it successful, #setSucceeded() must be called before the
     854     * instance is destroyed.
     855     *
     856     * Note that if an instance of this class gets constructed when the object
     857     * is in the state other than Limited, #isOk() returns |false| and methods
     858     * of this class do nothing: the state transition is not performed.
     859     *
     860     * A typical usage pattern is:
     861     * <code>
     862     * HRESULT Component::reinit()
     863     * {
     864     *     AutoReinitSpan autoReinitSpan (this);
     865     *     AssertReturn (autoReinitSpan.isOk(), E_UNEXPECTED);
     866     *     ...
     867     *     if (FAILED (rc))
     868     *         return rc;
     869     *     ...
     870     *     if (SUCCEEDED (rc))
     871     *         autoReinitSpan.setSucceeded();
     872     *     return rc;
     873     * }
     874     * </code>
     875     *
     876     * @note Never create instances of this class outside re-initialization
     877     * methods of VirtualBoxBase subclasses and never pass anything other than
     878     * |this| as the argument to the constructor!
     879     */
     880    class AutoReinitSpan
    787881    {
    788882    public:
    789883
    790         AutoReadySpan (VirtualBoxBaseNEXT_base *aObj);
    791         ~AutoReadySpan();
     884        AutoReinitSpan (VirtualBoxBaseProto *aObj);
     885        ~AutoReinitSpan();
    792886
    793887        /**
    794          *  Returns |true| if this instance has been created at the right moment
    795          *  (when the object was in the Limited state) and |false| otherwise.
     888         * Returns |true| if this instance has been created at the right moment
     889         * (when the object was in the Limited state) and |false| otherwise.
    796890         */
    797891        bool isOk() const { return mOk; }
    798892
    799893        /**
    800          *  Sets the re-initialization status to Succeeded to indicates
    801          *  successful re-initialization. The AutoReadySpan destructor will
    802          *  place the managed VirtualBoxBase object to the Ready state.
     894         * Sets the re-initialization status to Succeeded to indicates
     895         * successful re-initialization. The AutoReinitSpan destructor will place
     896         * the managed VirtualBoxBase object to the Ready state.
    803897         */
    804898        void setSucceeded() { mSucceeded = true; }
     
    806900    private:
    807901
    808         DECLARE_CLS_COPY_CTOR_ASSIGN_NOOP (AutoReadySpan)
    809         DECLARE_CLS_NEW_DELETE_NOOP (AutoReadySpan)
    810 
    811         VirtualBoxBaseNEXT_base *mObj;
     902        DECLARE_CLS_COPY_CTOR_ASSIGN_NOOP (AutoReinitSpan)
     903        DECLARE_CLS_NEW_DELETE_NOOP (AutoReinitSpan)
     904
     905        VirtualBoxBaseProto *mObj;
    812906        bool mSucceeded : 1;
    813907        bool mOk : 1;
     
    815909
    816910    /**
    817      *  Smart class to enclose the state transition Ready->InUnnit->NotReady or
    818      *  InitFailed->InUnnit->NotReady.
    819      *
    820      *  Must be created at the beginning of uninit() methods of VirtualBoxBase
    821      *  subclasses as a stack-based variable using |this| pointer as the argument.
    822      *  When this variable is created it automatically places the object to the
    823      *  InUninit state, unless it is already in the NotReady state as indicated
    824      *  by #uninitDone() returning |true|. In the latter case, the uninit()
    825      *  method must immediately return because there should be nothing to
    826      *  uninitialize.
    827      *
    828      *  When this variable goes out of scope (i.e. gets destroyed), it places
    829      *  the object to the NotReady state.
    830      *
    831      *  A typical usage pattern is:
    832      *  <code>
    833      *  void Component::uninit()
    834      *  {
    835      *      AutoUninitSpan autoUninitSpan (this);
    836      *      if (autoUninitSpan.uninitDone())
    837      *          retrun;
    838      *      ...
    839      *  </code>
    840      *
    841      *  @note Never create instances of this class outside uninit() methods and
    842      *  never pass anything other than |this| as the argument to the constructor!
     911     * Smart class to enclose the state transition Ready->InUnnit->NotReady,
     912     * InitFailed->InUnnit->NotReady or WillUninit->InUnnit->NotReady.
     913     *
     914     * The purpose of this span is to protect object uninitialization.
     915     *
     916     * Instances must be created as a stack-based variable taking |this| pointer
     917     * as the argument at the beginning of uninit() methods of VirtualBoxBase
     918     * subclasses. When this variable is created it automatically places the
     919     * object to the InUninit state, unless it is already in the NotReady state
     920     * as indicated by #uninitDone() returning |true|. In the latter case, the
     921     * uninit() method must immediately return because there should be nothing
     922     * to uninitialize.
     923     *
     924     * When this variable goes out of scope (i.e. gets destroyed), it places the
     925     * object to NotReady state.
     926     *
     927     * A typical usage pattern is:
     928     * <code>
     929     * void Component::uninit()
     930     * {
     931     *     AutoUninitSpan autoUninitSpan (this);
     932     *     if (autoUninitSpan.uninitDone())
     933     *         retrun;
     934     *     ...
     935     * }
     936     * </code>
     937     *
     938     * @note The constructor of this class blocks the current thread execution
     939     *       until the number of callers added to the object using #addCaller()
     940     *       or AutoCaller drops to zero. For this reason, it is forbidden to
     941     *       create instances of this class (or call uninit()) within the
     942     *       AutoCaller or #addCaller() scope because it is a guaranteed
     943     *       deadlock.
     944     *
     945     * @note Never create instances of this class outside uninit() methods and
     946     *       never pass anything other than |this| as the argument to the
     947     *       constructor!
    843948     */
    844949    class AutoUninitSpan
     
    846951    public:
    847952
    848         AutoUninitSpan (VirtualBoxBaseNEXT_base *aObj);
     953        AutoUninitSpan (VirtualBoxBaseProto *aObj);
    849954        ~AutoUninitSpan();
    850955
     
    860965        DECLARE_CLS_NEW_DELETE_NOOP (AutoUninitSpan)
    861966
    862         VirtualBoxBaseNEXT_base *mObj;
     967        VirtualBoxBaseProto *mObj;
    863968        bool mInitFailed : 1;
    864969        bool mUninitDone : 1;
     970    };
     971
     972    /**
     973     * Smart class to enclose the state transition Ready->MayUninit->NotReady or
     974     * Ready->MayUninit->WillUninit.
     975     *
     976     * The purpose of this span is to safely check if unintialization is
     977     * possible at the given moment and seamlessly perform it if so.
     978     *
     979     * Instances must be created as a stack-based variable taking |this| pointer
     980     * as the argument at the beginning of methods of VirtualBoxBase
     981     * subclasses that want to uninitialize the object if a necessary set of
     982     * criteria is met and leave it Ready otherwise.
     983     *
     984     * When this variable is created it automatically places the object to the
     985     * MayUninit state if it is Ready, does nothing but returns |true| in
     986     * response to #alreadyInProgress() if it is already in MayUninit, or
     987     * returns a failure in response to #rc() in any other case. The example
     988     * below shows how the user must react in latter two cases.
     989     *
     990     * When this variable goes out of scope (i.e. gets destroyed), it places the
     991     * object back to Ready state unless #acceptUninit() is called in which case
     992     * the object is placed to WillUninit state and uninit() is immediately
     993     * called after that.
     994     *
     995     * A typical usage pattern is:
     996     * <code>
     997     * void Component::uninit()
     998     * {
     999     *     AutoMayUninitSpan mayUninitSpan (this);
     1000     *     CheckComRCReturnRC (mayUninitSpan.rc());
     1001     *     if (mayUninitSpan.alreadyInProgress())
     1002     *          return S_OK;
     1003     *     ...
     1004     *     if (FAILED (rc))
     1005     *         return rc; // will go back to Ready
     1006     *     ...
     1007     *     if (SUCCEEDED (rc))
     1008     *         mayUninitSpan.acceptUninit(); // will call uninit()
     1009     *     return rc;
     1010     * }
     1011     * </code>
     1012     *
     1013     * @note The constructor of this class blocks the current thread execution
     1014     *       until the number of callers added to the object using #addCaller()
     1015     *       or AutoCaller drops to zero. For this reason, it is forbidden to
     1016     *       create instances of this class (or call uninit()) within the
     1017     *       AutoCaller or #addCaller() scope because it is a guaranteed
     1018     *       deadlock.
     1019     */
     1020    class AutoMayUninitSpan
     1021    {
     1022    public:
     1023
     1024        AutoMayUninitSpan (VirtualBoxBaseProto *aObj);
     1025        ~AutoMayUninitSpan();
     1026
     1027        /**
     1028         * Returns a failure if the AutoMayUninitSpan variable was constructed
     1029         * at an improper time. If there is a failure, do nothing but return
     1030         * it to the caller.
     1031         */
     1032        HRESULT rc() { return mRC; }
     1033
     1034        /**
     1035         * Returns |true| if AutoMayUninitSpan is already in progress on some
     1036         * other thread. If it's the case, do nothing but return S_OK to
     1037         * the caller.
     1038         */
     1039        bool alreadyInProgress() { return mAlreadyInProgress; }
     1040
     1041        /*
     1042         * Accepts uninitialization and causes the destructor to go to
     1043         * WillUninit state and call uninit() afterwards.
     1044         */
     1045        void acceptUninit() { mAcceptUninit = true; }
     1046
     1047    private:
     1048
     1049        DECLARE_CLS_COPY_CTOR_ASSIGN_NOOP (AutoMayUninitSpan)
     1050        DECLARE_CLS_NEW_DELETE_NOOP (AutoMayUninitSpan)
     1051
     1052        VirtualBoxBaseProto *mObj;
     1053
     1054        HRESULT mRC;
     1055        bool mAlreadyInProgress : 1;
     1056        bool mAcceptUninit : 1;
    8651057    };
    8661058
     
    8881080    /** Total number of active calls to this object */
    8891081    unsigned mCallers;
    890     /** Semaphore posted when the number of callers drops to zero */
     1082    /** Posted when the number of callers drops to zero */
    8911083    RTSEMEVENT mZeroCallersSem;
    892     /** Semaphore posted when the object goes from InInit some other state */
    893     RTSEMEVENTMULTI mInitDoneSem;
    894     /** Number of threads waiting for mInitDoneSem */
    895     unsigned mInitDoneSemUsers;
     1084    /** Posted when the object goes from InInit/InUninit to some other state */
     1085    RTSEMEVENTMULTI mInitUninitSem;
     1086    /** Number of threads waiting for mInitUninitDoneSem */
     1087    unsigned mInitUninitWaiters;
    8961088
    8971089    /** Protects access to state related data members */
     
    9011093    mutable RWLockHandle *mObjectLock;
    9021094};
     1095
     1096////////////////////////////////////////////////////////////////////////////////
    9031097
    9041098/**
     
    9181112 */
    9191113#define VIRTUALBOXBASE_ADD_ERRORINFO_SUPPORT(C) \
    920     virtual HRESULT addCaller (VirtualBoxBaseNEXT_base::State *aState = NULL, \
     1114    virtual HRESULT addCaller (VirtualBoxBaseProto::State *aState = NULL, \
    9211115                               bool aLimited = false) \
    9221116    { \
    923         VirtualBoxBaseNEXT_base::State state; \
    924         HRESULT rc = VirtualBoxBaseNEXT_base::addCaller (&state, aLimited); \
     1117        VirtualBoxBaseProto::State state; \
     1118        HRESULT rc = VirtualBoxBaseProto::addCaller (&state, aLimited); \
    9251119        if (FAILED (rc)) \
    9261120        { \
    927             if (state == VirtualBoxBaseNEXT_base::Limited) \
     1121            if (state == VirtualBoxBaseProto::Limited) \
    9281122                rc = setError (rc, tr ("The object functonality is limited")); \
    9291123            else \
     
    9381132
    9391133/// @todo (dmik) remove after we switch to VirtualBoxBaseNEXT completely
    940 class ATL_NO_VTABLE VirtualBoxBase : public VirtualBoxBaseNEXT_base
    941 //#if !defined (VBOX_WITH_XPCOM)
    942 //    : public CComObjectRootEx<CComMultiThreadModel>
    943 //#else
    944 //    : public CComObjectRootEx
    945 //#endif
     1134class ATL_NO_VTABLE VirtualBoxBase
     1135    : virtual public VirtualBoxBaseProto
     1136#if !defined (VBOX_WITH_XPCOM)
     1137    , public CComObjectRootEx <CComMultiThreadModel>
     1138#else
     1139    , public CComObjectRootEx
     1140#endif
    9461141{
    9471142
     
    9901185 *  Temporary class to disable deprecated methods of VirtualBoxBase.
    9911186 *  Can be used as a base for components that are completely switched to
    992  *  the new locking scheme (VirtualBoxBaseNEXT_base).
     1187 *  the new locking scheme (VirtualBoxBaseProto).
    9931188 *
    9941189 *  @todo remove after we switch to VirtualBoxBaseNEXT completely.
     
    10061201////////////////////////////////////////////////////////////////////////////////
    10071202
    1008 /** Helper for VirtualBoxSupportTranslation */
     1203/** Helper for VirtualBoxSupportTranslation. */
    10091204class VirtualBoxSupportTranslationBase
    10101205{
    10111206protected:
    1012     static bool cutClassNameFrom__PRETTY_FUNCTION__ (char *prettyFunctionName);
     1207    static bool cutClassNameFrom__PRETTY_FUNCTION__ (char *aPrettyFunctionName);
    10131208};
    10141209
    10151210/**
    1016  *  This template implements the NLS string translation support for the
    1017  *  given class by providing a #tr() function.
    1018  *
    1019  *  @param C    class that needs to support the string translation
    1020  *
    1021  *  @note
    1022  *      Every class that wants to use the #tr() function in its own methods must
    1023  *      inherit from this template, regardless of whether its base class (if any)
    1024  *      inherits from it or not! Otherwise, the translation service will not
    1025  *      work correctly. However, the declaration of the resulting class must
    1026  *      contain the VIRTUALBOXSUPPORTTRANSLATION_OVERRIDE(<ClassName>) macro
    1027  *      if one of its base classes also inherits from this template (to resolve
    1028  *      the ambiguity of the #tr() function).
     1211 * The VirtualBoxSupportTranslation template implements the NLS string
     1212 * translation support for the given class.
     1213 *
     1214 * Translation support is provided by the static #tr() function. This function,
     1215 * given a string in UTF-8 encoding, looks up for a translation of the given
     1216 * string by calling the VirtualBoxBase::translate() global function which
     1217 * receives the name of the enclosing class ("context of translation") as the
     1218 * additional argument and returns a translated string based on the currently
     1219 * active language.
     1220 *
     1221 * @param C     Class that needs to support the string translation.
     1222 *
     1223 * @note Every class that wants to use the #tr() function in its own methods
     1224 *       must inherit from this template, regardless of whether its base class
     1225 *       (if any) inherits from it or not. Otherwise, the translation service
     1226 *       will not work correctly. However, the declaration of the derived
     1227 *       class must contain
     1228 *       the <tt>COM_SUPPORTTRANSLATION_OVERRIDE (<ClassName>)</tt> macro if one
     1229 *       of its base classes also inherits from this template (to resolve the
     1230 *       ambiguity of the #tr() function).
    10291231 */
    10301232template <class C>
     
    10341236
    10351237    /**
    1036      *  Translates the given text string according to the currently installed
    1037      *  translation table and current context, which is determined by the
    1038      *  class name. See VirtualBoxBase::translate() for more info.
    1039      *
    1040      *  @param sourceText   the string to translate
    1041      *  @param comment      the comment to the string (NULL means no comment)
    1042      *
    1043      *  @return
    1044      *      the translated version of the source string in UTF-8 encoding,
    1045      *      or the source string itself if the translation is not found in
    1046      *      the current context.
    1047      */
    1048     inline static const char *tr (const char *sourceText, const char *comment = 0)
    1049     {
    1050         return VirtualBoxBase::translate (getClassName(), sourceText, comment);
     1238     * Translates the given text string by calling VirtualBoxBase::translate()
     1239     * and passing the name of the C class as the first argument ("context of
     1240     * translation") See VirtualBoxBase::translate() for more info.
     1241     *
     1242     * @param aSourceText   String to translate.
     1243     * @param aComment      Comment to the string to resolve possible
     1244     *                      ambiguities (NULL means no comment).
     1245     *
     1246     * @return Translated version of the source string in UTF-8 encoding, or
     1247     *      the source string itself if the translation is not found in the
     1248     *      specifiecd context.
     1249     */
     1250    inline static const char *tr (const char *aSourceText,
     1251                                  const char *aComment = NULL)
     1252    {
     1253        return VirtualBoxBase::translate (className(), aSourceText, aComment);
    10511254    }
    10521255
    10531256protected:
    10541257
    1055     static const char *getClassName()
     1258    static const char *className()
    10561259    {
    10571260        static char fn [sizeof (__PRETTY_FUNCTION__) + 1];
    1058         if (!className)
     1261        if (!sClassName)
    10591262        {
    10601263            strcpy (fn, __PRETTY_FUNCTION__);
    10611264            cutClassNameFrom__PRETTY_FUNCTION__ (fn);
    1062             className = fn;
     1265            sClassName = fn;
    10631266        }
    1064         return className;
     1267        return sClassName;
    10651268    }
    10661269
    10671270private:
    10681271
    1069     static const char *className;
     1272    static const char *sClassName;
    10701273};
    10711274
    10721275template <class C>
    1073 const char *VirtualBoxSupportTranslation <C>::className = NULL;
     1276const char *VirtualBoxSupportTranslation <C>::sClassName = NULL;
    10741277
    10751278/**
    1076  *  This macro must be invoked inside the public section of the declaration of
    1077  *  the class inherited from the VirtualBoxSupportTranslation template, in case
    1078  *  when one of its other base classes also inherits from that template. This is
    1079  *  necessary to resolve the ambiguity of the #tr() function.
    1080  *
    1081  *  @param C    class that inherits from the VirtualBoxSupportTranslation template
    1082  *              more than once (through its other base clases)
     1279 * This macro must be invoked inside the public section of the declaration of
     1280 * the class inherited from the VirtualBoxSupportTranslation template in case
     1281 * if one of its other base classes also inherits from that template. This is
     1282 * necessary to resolve the ambiguity of the #tr() function.
     1283 *
     1284 * @param C     Class that inherits the VirtualBoxSupportTranslation template
     1285 *              more than once (through its other base clases).
    10831286 */
    10841287#define VIRTUALBOXSUPPORTTRANSLATION_OVERRIDE(C) \
    1085     inline static const char *tr (const char *sourceText, const char *comment = 0) \
     1288    inline static const char *tr (const char *aSourceText, \
     1289                                  const char *aComment = NULL) \
    10861290    { \
    1087         return VirtualBoxSupportTranslation <C>::tr (sourceText, comment); \
     1291        return VirtualBoxSupportTranslation <C>::tr (aSourceText, aComment); \
    10881292    }
    10891293
    10901294/**
    1091  *  A dummy macro that is used to shut down Qt's lupdate tool warnings
    1092  *  in some situations. This macro needs to be present inside (better at the
    1093  *  very beginning) of the declaration of the class that inherits from
    1094  *  VirtualBoxSupportTranslation template, to make lupdate happy.
     1295 * Dummy macro that is used to shut down Qt's lupdate tool warnings in some
     1296 * situations. This macro needs to be present inside (better at the very
     1297 * beginning) of the declaration of the class that inherits from
     1298 * VirtualBoxSupportTranslation template, to make lupdate happy.
    10951299 */
    10961300#define Q_OBJECT
     
    11011305 *  Helper for the VirtualBoxSupportErrorInfoImpl template.
    11021306 */
     1307/// @todo switch to com::SupportErrorInfo* and remove
    11031308class VirtualBoxSupportErrorInfoImplBase
    11041309{
     
    11101315
    11111316    /**
    1112      * The MultiResult class is a com::LWResult enhancement that also acts as a
     1317     * The MultiResult class is a com::FWResult enhancement that also acts as a
    11131318     * switch to turn on multi-error mode for #setError() or #setWarning()
    11141319     * calls.
     
    11411346     * doesn't return control return to the caller immediately after the first
    11421347     * error or warning but continues its execution, the functionality provided
    1143      * by the base com::LWResult class becomes very useful because it allows to
     1348     * by the base com::FWResult class becomes very useful because it allows to
    11441349     * preseve the error or the warning result code even if it is later assigned
    1145      * a S_OK value multiple times. See com::LWResult for details.
     1350     * a S_OK value multiple times. See com::FWResult for details.
    11461351     *
    11471352     * Here is the typical usage pattern:
     
    11811386     *       You cannot create them using new(). Although it is possible to copy
    11821387     *       instances of MultiResult or return them by value, please never do
    1183      *       that as it is breaks the class semantics (and will assert);
    1184      */
    1185     class MultiResult : public com::LWResult
     1388     *       that as it is breaks the class semantics (and will assert).
     1389     */
     1390    class MultiResult : public com::FWResult
    11861391    {
    11871392    public:
    11881393
    11891394        /**
    1190          * @see com::LWResult::LWResult().
     1395         * @copydoc com::FWResult::FWResult().
    11911396         */
    1192         MultiResult (HRESULT aRC = E_FAIL) : LWResult (aRC) { init(); }
    1193 
    1194         MultiResult (const MultiResult &aThat) : LWResult (aThat)
     1397        MultiResult (HRESULT aRC = E_FAIL) : FWResult (aRC) { init(); }
     1398
     1399        MultiResult (const MultiResult &aThat) : FWResult (aThat)
    11951400        {
    11961401            /* We need this copy constructor only for GCC that wants to have
     
    12061411        MultiResult &operator= (HRESULT aRC)
    12071412        {
    1208             com::LWResult::operator= (aRC);
     1413            com::FWResult::operator= (aRC);
    12091414            return *this;
    12101415        }
     
    12171422             * temporary and call the other constructor directly istead. */
    12181423            AssertFailed();
    1219             com::LWResult::operator= (aThat);
     1424            com::FWResult::operator= (aThat);
    12201425            return *this;
    12211426        }
     
    12911496 *      by the shortest form of #setError, for convenience.
    12921497 */
     1498/// @todo switch to com::SupportErrorInfo* and remove
    12931499template <class C, class I>
    12941500class ATL_NO_VTABLE VirtualBoxSupportErrorInfoImpl
     
    17131919
    17141920/**
    1715  *
    17161921 * Base class to track VirtualBoxBaseNEXT chlidren of the component.
    17171922 *
     
    18042009
    18052010    /**
     2011     * Equivalent to template <class C> void addDependentChild (C *aChild)
     2012     * but takes a ComObjPtr <C> argument.
     2013     */
     2014    template <class C>
     2015    void addDependentChild (const ComObjPtr <C> &aChild)
     2016    {
     2017        AssertReturnVoid (!aChild.isNull());
     2018        doAddDependentChild (ComPtr <IUnknown> (static_cast <C *> (aChild)), aChild);
     2019    }
     2020
     2021    /**
    18062022     * Removes the given child from the map of dependent children.
    18072023     *
    1808      * Make sure this method is called after the child has successfully entered
    1809      * AutoUninitSpan and outside the child lock.
     2024     * Typically called from from the child's uninit() method, from within the
     2025     * AutoUninitSpan scope. Make sure te child is not locked for reading or
     2026     * writing in this case.
    18102027     *
    18112028     * If called not from within the AutoUninitSpan scope,
     
    18202037    {
    18212038        AssertReturnVoid (aChild);
    1822         Assert (!aChild->isWriteLockOnCurrentThread());
    18232039        doRemoveDependentChild (ComPtr <IUnknown> (aChild));
     2040    }
     2041
     2042    /**
     2043     * Equivalent to template <class C> void removeDependentChild (C *aChild)
     2044     * but takes a ComObjPtr <C> argument.
     2045     */
     2046    template <class C>
     2047    void removeDependentChild (const ComObjPtr <C> &aChild)
     2048    {
     2049        AssertReturnVoid (!aChild.isNull());
     2050        doRemoveDependentChild (ComPtr <IUnknown> (static_cast <C *> (aChild)));
    18242051    }
    18252052
     
    19272154    /**
    19282155     *  Returns an internal lock handle to lock the list of children
    1929      *  returned by #dependentChildren() using AutoWriteLock:
     2156     *  returned by #dependentChildren() using AutoReadLock/AutoWriteLock:
    19302157     *  <code>
    1931      *      AutoWriteLock alock (dependentChildrenLock());
     2158     *      AutoReadLock alock (dependentChildrenLock());
    19322159     *  </code>
     2160     *
     2161     *  This is necessary for example to access the list of children returned by
     2162     *  #dependentChildren().
    19332163     */
    19342164    RWLockHandle *dependentChildrenLock() const { return &mMapLock; }
     
    20102240 * This class is similar to VirtualBoxBaseWithChildren, with the exception that
    20112241 * all children must be of the same type. For this reason, it's not necessary to
    2012  * use a map to store children, so a list is used instead.
    2013  *
    2014  * As opposed to VirtualBoxBaseWithChildren, children added by
     2242 * use a map to store children -- a list is used instead.
     2243 *
     2244 * Also, as opposed to VirtualBoxBaseWithChildren, children added by
    20152245 * #addDependentChild() are <b>strongly</b> referenced, so that they cannot be
    2016  * externally deleted until #removeDependentChild() is called. For this
    2017  * reason, strict rules of calling #removeDependentChild() don't apply to
    2018  * instances of this class -- it can be called anywhere in the child's uninit()
    2019  * implementation.
     2246 * deleted until #removeDependentChild() is called on them.
     2247 *
     2248 * See individual method descriptions for more information.
    20202249 *
    20212250 * @param C Type of child objects (must inherit VirtualBoxBase AND implementsome
     
    20342263    typedef std::list <ComObjPtr <C> > DependentChildren;
    20352264
    2036     VirtualBoxBaseWithTypedChildrenNEXT() : mInUninit (false) {}
     2265    VirtualBoxBaseWithTypedChildrenNEXT() {}
    20372266
    20382267    virtual ~VirtualBoxBaseWithTypedChildrenNEXT() {}
     
    20412270     * Adds the given child to the list of dependent children.
    20422271     *
    2043      * VirtualBoxBase::AutoCaller must be used on @a aChild to make sure it is
    2044      * not uninitialized during this method's call.
    2045      *
    2046      *  @param aChild   Child object to add (must inherit VirtualBoxBase AND
    2047      *                  implement some interface).
     2272     * Usually gets called from the child's init() method.
     2273     *
     2274     * @note Locks this object for writing.
     2275     *
     2276     * @note @a aChild (unless it is in InInit state) must be protected by
     2277     *       VirtualBoxBase::AutoCaller to make sure it is not uninitialized on
     2278     *       another thread during this method's call.
     2279     *
     2280     * @note If this method is called from under the child's read or write lock,
     2281     *       make sure the {parent, child} locking order is preserved by locking
     2282     *       the callee (this object) for writing before the child's lock.
     2283     *
     2284     * @param aChild    Child object to add.
    20482285     */
    20492286    void addDependentChild (C *aChild)
     
    20512288        AssertReturnVoid (aChild);
    20522289
    2053         AutoWriteLock alock (mMapLock);
    2054         if (mInUninit)
     2290        AutoCaller autoCaller (this);
     2291
     2292        /* sanity */
     2293        AssertReturnVoid (autoCaller.state() == InInit ||
     2294                          autoCaller.state() == Ready ||
     2295                          autoCaller.state() == Limited);
     2296
     2297        AutoWriteLock alock (this);
     2298        mDependentChildren.push_back (aChild);
     2299    }
     2300
     2301    /**
     2302     * Removes the given child from the list of dependent children.
     2303     *
     2304     * Usually gets called from the child's uninit() method.
     2305     *
     2306     * Note that once this method returns, the callee (this object) is not
     2307     * guaranteed to be valid any more, so the caller must not call its
     2308     * other methods.
     2309     *
     2310     * @note Locks this object for writing.
     2311     *
     2312     * @note @a aChild (unless it is in InUninit state) must be protected by
     2313     *       VirtualBoxBase::AutoCaller to make sure it is not uninitialized on
     2314     *       another thread during this method's call.
     2315     *
     2316     * @note If this method is called from under the child's read or write lock,
     2317     *       make sure the {parent, child} locking order is preserved by locking
     2318     *       the callee (this object) for writing before the child's lock.
     2319     *
     2320     * @param aChild    Child object to remove.
     2321     */
     2322    void removeDependentChild (C *aChild)
     2323    {
     2324        AssertReturnVoid (aChild);
     2325
     2326        AutoCaller autoCaller (this);
     2327
     2328        /* return shortly; uninitDependentChildren() will do the job */
     2329        if (autoCaller.state() == InUninit)
    20552330            return;
    20562331
    2057         mDependentChildren.push_back (aChild);
    2058     }
    2059 
    2060     /**
    2061      * Removes the given child from the list of dependent children.
    2062      *
    2063      * VirtualBoxBase::AutoCaller must be used on @a aChild to make sure it is
    2064      * not uninitialized during this method's call.
    2065      *
    2066      *  @param aChild   the child object to remove (must inherit VirtualBoxBase
    2067      *                  AND implement some interface).
    2068      */
    2069     void removeDependentChild (C *aChild)
    2070     {
    2071         AssertReturnVoid (aChild);
    2072 
    2073         AutoWriteLock alock (mMapLock);
    2074         if (mInUninit)
    2075             return;
    2076 
     2332        AutoWriteLock alock (this);
    20772333        mDependentChildren.remove (aChild);
    20782334    }
     
    20812337
    20822338    /**
    2083      * Returns an internal lock handle used to lock the list of children
    2084      * returned by #dependentChildren(). This lock is to be used by
    2085      * AutoWriteLock as follows:
    2086      * <code>
    2087      *      AutoWriteLock alock (dependentChildrenLock());
    2088      * </code>
    2089      */
    2090     RWLockHandle *dependentChildrenLock() const { return &mMapLock; }
    2091 
    2092     /**
    20932339     * Returns the read-only list of all dependent children.
    20942340     *
    2095      * @note Access the returned list (iterate, get size etc.) only after doing
    2096      *       AutoWriteLock alock (dependentChildrenLock())!
     2341     * @note Access the returned list (iterate, get size etc.) only after
     2342     *       locking this object for reading or for writing!
    20972343     */
    20982344    const DependentChildren &dependentChildren() const { return mDependentChildren; }
    20992345
    2100     void uninitDependentChildren();
     2346    /**
     2347     * Uninitializes all dependent children registered on this object with
     2348     * #addDependentChild().
     2349     *
     2350     * Must be called from within the VirtualBoxBaseProto::AutoUninitSpan (i.e.
     2351     * typically from this object's uninit() method) to uninitialize children
     2352     * before this object goes out of service and becomes unusable.
     2353     *
     2354     * Note that this method will call uninit() methods of child objects. If
     2355     * these methods need to call the parent object during uninitialization,
     2356     * #uninitDependentChildren() must be called before the relevant part of the
     2357     * parent is uninitialized, usually at the begnning of the parent
     2358     * uninitialization sequence.
     2359     *
     2360     * @note May lock this object through the called children.
     2361     */
     2362    void uninitDependentChildren()
     2363    {
     2364        AutoCaller autoCaller (this);
     2365
     2366        /* We cannot hold the write lock (necessary here to protect
     2367         * mDependentChildren) when uninitializing children because we want to
     2368         * avoid a possible deadlock where we could get stuck in child->uninit()
     2369         * blocked by AutoUninitSpan waiting for the number of child's callers
     2370         * to drop to zero, while some caller is stuck in our
     2371         * removeDependentChild() method waiting for the write lock.
     2372         *
     2373         * The only safe place to not lock and keep accessing our data members
     2374         * is the InUninit state (no active call to our object may exist on
     2375         * another thread when we are in InUinint, provided that all such calls
     2376         * use the AutoCaller class of course). InUinint is also used as a flag
     2377         * by removeDependentChild() that prevents touching mDependentChildren
     2378         * from outside. Therefore, we assert.
     2379         */
     2380        AssertReturnVoid (autoCaller.state() == InUninit);
     2381
     2382        if (mDependentChildren.size())
     2383        {
     2384            for (typename DependentChildren::iterator it = mDependentChildren.begin();
     2385                 it != mDependentChildren.end(); ++ it)
     2386            {
     2387                C *child = (*it);
     2388                Assert (child);
     2389
     2390                /* Note that if child->uninit() happens to be called on another
     2391                 * thread right before us and is not yet finished; the second
     2392                 * uninit() call will wait until the first one has done so
     2393                 * (thanks to AutoUninitSpan). */
     2394                if (child)
     2395                    child->uninit();
     2396            }
     2397
     2398            /* release all strong references we hold */
     2399            mDependentChildren.clear();
     2400        }
     2401    }
    21012402
    21022403    /**
     
    21042405     * #addDependentChild(), without uninitializing them.
    21052406     *
    2106      * @note This method must be called from under the main object's lock.
     2407     * @note @a |this| (unless it is in InUninit state) must be protected by
     2408     *       VirtualBoxBase::AutoCaller to make sure it is not uninitialized on
     2409     *       another thread during this method's call.
     2410     *
     2411     * @note Locks this object for writing.
    21072412     */
    21082413    void removeDependentChildren()
    21092414    {
    2110         /// @todo why?..
    2111         AssertReturnVoid (isWriteLockOnCurrentThread());
    2112 
    2113         AutoWriteLock alock (mMapLock);
     2415        AutoWriteLock alock (this);
    21142416        mDependentChildren.clear();
    21152417    }
     
    21182420
    21192421    DependentChildren mDependentChildren;
    2120 
    2121     bool mInUninit;
    2122 
    2123     /* Protects the two fields above */
    2124     mutable RWLockHandle mMapLock;
    21252422};
    21262423
  • trunk/src/VBox/Main/include/VirtualBoxImpl.h

    r13457 r13580  
    4444class Machine;
    4545class SessionMachine;
    46 class HardDisk;
    47 class HVirtualDiskImage;
    48 class DVDImage;
    49 class FloppyImage;
     46class HardDisk2;
     47class DVDImage2;
     48class FloppyImage2;
    5049class MachineCollection;
    51 class HardDiskCollection;
    52 class DVDImageCollection;
    53 class FloppyImageCollection;
    5450class GuestOSType;
    5551class GuestOSTypeCollection;
     
    128124    STDMETHOD(COMGETTER(Host)) (IHost **aHost);
    129125    STDMETHOD(COMGETTER(SystemProperties)) (ISystemProperties **aSystemProperties);
    130     STDMETHOD(COMGETTER(Machines)) (IMachineCollection **aMachines);
    131126    STDMETHOD(COMGETTER(Machines2)) (ComSafeArrayOut (IMachine *, aMachines));
    132     STDMETHOD(COMGETTER(HardDisks)) (IHardDiskCollection **aHardDisks);
    133     STDMETHOD(COMGETTER(DVDImages)) (IDVDImageCollection **aDVDImages);
    134     STDMETHOD(COMGETTER(FloppyImages)) (IFloppyImageCollection **aFloppyImages);
     127    STDMETHOD(COMGETTER(HardDisks2)) (ComSafeArrayOut (IHardDisk2 *, aHardDisks));
     128    STDMETHOD(COMGETTER(DVDImages)) (ComSafeArrayOut (IDVDImage2 *, aDVDImages));
     129    STDMETHOD(COMGETTER(FloppyImages)) (ComSafeArrayOut (IFloppyImage2 *, aFloppyImages));
    135130    STDMETHOD(COMGETTER(ProgressOperations)) (IProgressCollection **aOperations);
    136131    STDMETHOD(COMGETTER(GuestOSTypes)) (IGuestOSTypeCollection **aGuestOSTypes);
     
    150145    STDMETHOD(UnregisterMachine) (INPTR GUIDPARAM aId, IMachine **aMachine);
    151146
    152     STDMETHOD(CreateHardDisk) (HardDiskStorageType_T aStorageType, IHardDisk **aHardDisk);
    153     STDMETHOD(OpenHardDisk) (INPTR BSTR aLocation, IHardDisk **aHardDisk);
    154     STDMETHOD(OpenVirtualDiskImage) (INPTR BSTR aFilePath, IVirtualDiskImage **aImage);
    155     STDMETHOD(RegisterHardDisk) (IHardDisk *aHardDisk);
    156     STDMETHOD(GetHardDisk) (INPTR GUIDPARAM aId, IHardDisk **aHardDisk);
    157     STDMETHOD(FindHardDisk) (INPTR BSTR aLocation, IHardDisk **aHardDisk);
    158     STDMETHOD(FindVirtualDiskImage) (INPTR BSTR aFilePath, IVirtualDiskImage **aImage);
    159     STDMETHOD(UnregisterHardDisk) (INPTR GUIDPARAM aId, IHardDisk **aHardDisk);
    160 
    161     STDMETHOD(OpenDVDImage) (INPTR BSTR aFilePath, INPTR GUIDPARAM aId,
    162                              IDVDImage **aDVDImage);
    163     STDMETHOD(RegisterDVDImage) (IDVDImage *aDVDImage);
    164     STDMETHOD(GetDVDImage) (INPTR GUIDPARAM aId, IDVDImage **aDVDImage);
    165     STDMETHOD(FindDVDImage) (INPTR BSTR aFilePath, IDVDImage **aDVDImage);
    166     STDMETHOD(GetDVDImageUsage) (INPTR GUIDPARAM aId,
    167                                  ResourceUsage_T aUsage,
    168                                  BSTR *aMachineIDs);
    169     STDMETHOD(UnregisterDVDImage) (INPTR GUIDPARAM aId, IDVDImage **aDVDImage);
    170 
    171     STDMETHOD(OpenFloppyImage) (INPTR BSTR aFilePath, INPTR GUIDPARAM aId,
    172                                 IFloppyImage **aFloppyImage);
    173     STDMETHOD(RegisterFloppyImage) (IFloppyImage *aFloppyImage);
    174     STDMETHOD(GetFloppyImage) (INPTR GUIDPARAM id, IFloppyImage **aFloppyImage);
    175     STDMETHOD(FindFloppyImage) (INPTR BSTR aFilePath, IFloppyImage **aFloppyImage);
    176     STDMETHOD(GetFloppyImageUsage) (INPTR GUIDPARAM aId,
    177                                     ResourceUsage_T aUsage,
    178                                     BSTR *aMachineIDs);
    179     STDMETHOD(UnregisterFloppyImage) (INPTR GUIDPARAM aId, IFloppyImage **aFloppyImage);
     147    STDMETHOD(CreateHardDisk2) (INPTR BSTR aFormat, INPTR BSTR aLocation,
     148                                IHardDisk2 **aHardDisk);
     149    STDMETHOD(OpenHardDisk2) (INPTR BSTR aLocation, IHardDisk2 **aHardDisk);
     150    STDMETHOD(GetHardDisk2) (INPTR GUIDPARAM aId, IHardDisk2 **aHardDisk);
     151    STDMETHOD(FindHardDisk2) (INPTR BSTR aLocation, IHardDisk2 **aHardDisk);
     152
     153    STDMETHOD(OpenDVDImage) (INPTR BSTR aLocation, INPTR GUIDPARAM aId,
     154                             IDVDImage2 **aDVDImage);
     155    STDMETHOD(GetDVDImage) (INPTR GUIDPARAM aId, IDVDImage2 **aDVDImage);
     156    STDMETHOD(FindDVDImage) (INPTR BSTR aLocation, IDVDImage2 **aDVDImage);
     157
     158    STDMETHOD(OpenFloppyImage) (INPTR BSTR aLocation, INPTR GUIDPARAM aId,
     159                                IFloppyImage2 **aFloppyImage);
     160    STDMETHOD(GetFloppyImage) (INPTR GUIDPARAM aId, IFloppyImage2 **aFloppyImage);
     161    STDMETHOD(FindFloppyImage) (INPTR BSTR aLocation, IFloppyImage2 **aFloppyImage);
    180162
    181163    STDMETHOD(GetGuestOSType) (INPTR BSTR aId, IGuestOSType **aType);
     
    241223    }
    242224
    243     /// @todo (dmik) remove and make findMachine() public instead
    244     //  after switching to VirtualBoxBaseNEXT
    245     HRESULT getMachine (const Guid &aId, ComObjPtr <Machine> &aMachine,
    246                         bool aSetError = false)
    247     {
    248         return findMachine (aId, aSetError, &aMachine);
    249     }
    250 
    251     /// @todo (dmik) remove and make findHardDisk() public instead
    252     //  after switching to VirtualBoxBaseNEXT
    253     HRESULT getHardDisk (const Guid &aId, ComObjPtr <HardDisk> &aHardDisk)
    254     {
    255         return findHardDisk (&aId, NULL, true /* aDoSetError */, &aHardDisk);
    256     }
    257 
    258     bool getDVDImageUsage (const Guid &aId, ResourceUsage_T aUsage,
    259                            Bstr *aMachineIDs = NULL);
    260     bool getFloppyImageUsage (const Guid &aId, ResourceUsage_T aUsage,
    261                               Bstr *aMachineIDs = NULL);
     225    HRESULT findMachine (const Guid &aId, bool aSetError,
     226                         ComObjPtr <Machine> *machine = NULL);
     227
     228    HRESULT findHardDisk2 (const Guid *aId, const BSTR aLocation,
     229                           bool aSetError, ComObjPtr <HardDisk2> *aHardDisk = NULL);
     230    HRESULT findDVDImage2 (const Guid *aId, const BSTR aLocation,
     231                           bool aSetError, ComObjPtr <DVDImage2> *aImage = NULL);
     232    HRESULT findFloppyImage2 (const Guid *aId, const BSTR aLocation,
     233                              bool aSetError, ComObjPtr <FloppyImage2> *aImage = NULL);
    262234
    263235    const ComObjPtr <Host> &host() { return mData.mHost; }
     
    273245    const Utf8Str &homeDir() { return mData.mHomeDir; }
    274246
     247    int calculateFullPath (const char *aPath, Utf8Str &aResult);
    275248    void calculateRelativePath (const char *aPath, Utf8Str &aResult);
    276249
    277     enum RHD_Flags { RHD_Internal, RHD_External, RHD_OnStartUp };
    278     HRESULT registerHardDisk (HardDisk *aHardDisk, RHD_Flags aFlags);
    279     HRESULT unregisterHardDisk (HardDisk *aHardDisk);
    280     HRESULT unregisterDiffHardDisk (HardDisk *aHardDisk);
     250    HRESULT registerHardDisk2 (HardDisk2 *aHardDisk, bool aSaveRegistry = true);
     251    HRESULT unregisterHardDisk2 (HardDisk2 *aHardDisk, bool aSaveRegistry = true);
     252
     253    HRESULT registerDVDImage (DVDImage2 *aImage, bool aSaveRegistry = true);
     254    HRESULT unregisterDVDImage (DVDImage2 *aImage, bool aSaveRegistry = true);
     255
     256    HRESULT registerFloppyImage (FloppyImage2 *aImage, bool aSaveRegistry = true);
     257    HRESULT unregisterFloppyImage (FloppyImage2 *aImage, bool aSaveRegistry = true);
     258
     259    HRESULT cast (IHardDisk2 *aFrom, ComObjPtr <HardDisk2> &aTo);
    281260
    282261    HRESULT saveSettings();
     
    284263
    285264    const Bstr &settingsFileName() { return mData.mCfgFile.mName; }
     265
     266    static HRESULT ensureFilePathExists (const char *aFileName);
    286267
    287268    class SettingsTreeHelper : public settings::XmlTreeBackend::InputResolver
     
    359340    static HRESULT handleUnexpectedExceptions (RT_SRC_POS_DECL);
    360341
     342    /**
     343     * Returns a lock handle used to protect changes to the hard disk hierarchy
     344     * (e.g. changing HardDisk2::mParent fields and adding/removing children).
     345     */
     346    RWLockHandle *hardDiskTreeHandle() { return &mHardDiskTreeHandle; }
     347
    361348    /* for VirtualBoxSupportErrorInfoImpl */
    362349    static const wchar_t *getComponentName() { return L"VirtualBox"; }
     
    366353    typedef std::list <ComObjPtr <Machine> > MachineList;
    367354    typedef std::list <ComObjPtr <GuestOSType> > GuestOSTypeList;
    368     typedef std::list <ComPtr <IProgress> > ProgressList;
    369 
    370     typedef std::list <ComObjPtr <HardDisk> > HardDiskList;
    371     typedef std::list <ComObjPtr <DVDImage> > DVDImageList;
    372     typedef std::list <ComObjPtr <FloppyImage> > FloppyImageList;
     355
     356    typedef std::map <Guid, ComPtr <IProgress> > ProgressMap;
     357
     358    typedef std::list <ComObjPtr <HardDisk2> > HardDisk2List;
     359    typedef std::list <ComObjPtr <DVDImage2> > DVDImage2List;
     360    typedef std::list <ComObjPtr <FloppyImage2> > FloppyImage2List;
    373361    typedef std::list <ComObjPtr <SharedFolder> > SharedFolderList;
    374362
    375     typedef std::map <Guid, ComObjPtr <HardDisk> > HardDiskMap;
    376 
    377     HRESULT findMachine (const Guid &aId, bool aSetError,
    378                          ComObjPtr <Machine> *machine = NULL);
    379 
    380     HRESULT findHardDisk (const Guid *aId, const BSTR aLocation,
    381                           bool aSetError, ComObjPtr <HardDisk> *aHardDisk = NULL);
    382 
    383     HRESULT findVirtualDiskImage (const Guid *aId, const BSTR aFilePathFull,
    384                           bool aSetError, ComObjPtr <HVirtualDiskImage> *aImage = NULL);
    385     HRESULT findDVDImage (const Guid *aId, const BSTR aFilePathFull,
    386                           bool aSetError, ComObjPtr <DVDImage> *aImage = NULL);
    387     HRESULT findFloppyImage (const Guid *aId, const BSTR aFilePathFull,
    388                              bool aSetError, ComObjPtr <FloppyImage> *aImage = NULL);
    389 
    390     HRESULT checkMediaForConflicts (HardDisk *aHardDisk,
    391                                     const Guid *aId, const BSTR aFilePathFull);
     363    typedef std::map <Guid, ComObjPtr <HardDisk2> > HardDisk2Map;
     364
     365    HRESULT checkMediaForConflicts2 (const Guid &aId, const Bstr &aLocation,
     366                                     Utf8Str &aConflictType);
    392367
    393368    HRESULT loadMachines (const settings::Key &aGlobal);
    394     HRESULT loadDisks (const settings::Key &aGlobal);
    395     HRESULT loadHardDisks (const settings::Key &aNode);
    396 
    397     HRESULT saveHardDisks (settings::Key &aNode);
     369    HRESULT loadMedia (const settings::Key &aGlobal);
    398370
    399371    HRESULT registerMachine (Machine *aMachine);
    400 
    401     HRESULT registerDVDImage (DVDImage *aImage, bool aOnStartUp);
    402     HRESULT registerFloppyImage (FloppyImage *aImage, bool aOnStartUp);
    403372
    404373    HRESULT lockConfig();
     
    442411        GuestOSTypeList mGuestOSTypes;
    443412
    444         ProgressList mProgressOperations;
    445         HardDiskList mHardDisks;
    446         DVDImageList mDVDImages;
    447         FloppyImageList mFloppyImages;
     413        ProgressMap mProgressOperations;
     414
     415        HardDisk2List mHardDisks2;
     416        DVDImage2List mDVDImages2;
     417        FloppyImage2List mFloppyImages2;
    448418        SharedFolderList mSharedFolders;
    449419
    450         HardDiskMap mHardDiskMap;
     420        /// @todo NEWMEDIA do we really need this map? Used only in
     421        /// find() it seems
     422        HardDisk2Map mHardDisk2Map;
    451423
    452424        CallbackList mCallbacks;
     
    490462    const RTTHREAD mAsyncEventThread;
    491463    EventQueue * const mAsyncEventQ;
    492     /** Lock for calling EventQueue->post() */
    493     RWLockHandle mAsyncEventQLock;
     464
     465    /**
     466     * "Safe" lock. May only be used if guaranteed that no other locks are
     467     * requested while holding it and no functions that may do so are called.
     468     * Currently, protects the following:
     469     *
     470     * - mProgressOperations
     471     */
     472    RWLockHandle mSafeLock;
     473
     474    RWLockHandle mHardDiskTreeHandle;
    494475
    495476    static Bstr sVersion;
  • trunk/src/VBox/Main/include/VirtualBoxXMLUtil.h

    r8155 r13580  
    2929
    3030/** VirtualBox XML settings version number substring ("x.y")  */
    31 #define VBOX_XML_VERSION        "1.3"
     31#define VBOX_XML_VERSION        "1.4"
    3232
    3333/** VirtualBox XML settings version platform substring */
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