VirtualBox

Changeset 79747 in vbox


Ignore:
Timestamp:
Jul 12, 2019 11:00:54 PM (6 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
132112
Message:

Main: Redoing the IDHCPServer interface, part II. Implemented groups and fixed a couple of bugs. Made RTNetStrToMacAddr understand hexstrings w/o colon separators. bugref:9288

Location:
trunk
Files:
7 edited

Legend:

Unmodified
Added
Removed
  • trunk/include/VBox/settings.h

    r79732 r79747  
    349349typedef DhcpOptionMap::const_iterator DhcpOptConstIterator;
    350350
     351struct DHCPGroupCondition
     352{
     353    DHCPGroupCondition();
     354
     355    bool                    fInclusive;
     356    DHCPGroupConditionType_T enmType;
     357    com::Utf8Str            strValue;
     358};
     359typedef std::vector<DHCPGroupCondition> DHCPGroupConditionVec;
     360
     361
    351362struct DHCPConfig
    352363{
    353364    DHCPConfig();
    354365
    355     DhcpOptionMap           OptionMap;
     366    DhcpOptionMap           mapOptions;
    356367    uint32_t                secMinLeaseTime;
    357368    uint32_t                secDefaultLeaseTime;
     
    359370};
    360371
     372struct DHCPGroupConfig : DHCPConfig
     373{
     374    DHCPGroupConfig();
     375
     376    com::Utf8Str            strName;
     377    DHCPGroupConditionVec   vecConditions;
     378};
     379typedef std::vector<DHCPGroupConfig> DHCPGroupConfigVec;
     380
    361381struct DHCPIndividualConfig : DHCPConfig
    362382{
     
    365385    com::Utf8Str            strMACAddress;
    366386    com::Utf8Str            strVMName;
    367     ULONG                   uSlot;
     387    uint32_t                uSlot;
    368388    com::Utf8Str            strFixedAddress;
    369389};
    370 
    371390typedef std::map<com::Utf8Str, DHCPIndividualConfig> DHCPIndividualConfigMap;
    372391
     
    380399    com::Utf8Str            strIPUpper;
    381400    bool                    fEnabled;
    382     DHCPConfig              GlobalConfig;
    383     DHCPIndividualConfigMap IndividualConfigs;
    384 };
    385 
     401    DHCPConfig              globalConfig;
     402    DHCPGroupConfigVec      vecGroupConfigs;
     403    DHCPIndividualConfigMap mapIndividualConfigs;
     404};
    386405typedef std::list<DHCPServer> DHCPServersList;
    387406
  • trunk/src/VBox/Main/idl/VirtualBox.xidl

    r79732 r79747  
    16421642
    16431643  <!--
    1644   // IVirtualBox
     1644  // INATNetwork
    16451645  /////////////////////////////////////////////////////////////////////////
    16461646  -->
     
    17541754    <method name="stop"/>
    17551755  </interface>
     1756
     1757
     1758  <!--
     1759  // IDHCPServer and associates
     1760  /////////////////////////////////////////////////////////////////////////
     1761  -->
    17561762
    17571763  <enum
     
    18321838  <enum
    18331839      name="DHCPConfigScope"
    1834       uuid="151df7cd-e596-42dd-235a-b164a781c099">
     1840      uuid="469c42e4-b9ec-43f2-bdcb-9e9d1eb434ae">
    18351841    <const name="Global"      value="0"><desc><link to="IDHCPServer::globalConfig"/></desc></const>
    1836     <const name="MachineNIC"  value="1"><desc><link to="IDHCPServer::individualConfigs"/></desc></const>
    1837     <const name="MAC"         value="2"><desc><link to="IDHCPServer::individualConfigs"/></desc></const>
    1838     <const name="Group"       value="3"><desc><link to="IDHCPServer::groupConfigs"/></desc></const>
     1842    <const name="Group"       value="1"><desc><link to="IDHCPServer::groupConfigs"/></desc></const>
     1843    <const name="MachineNIC"  value="2"><desc><link to="IDHCPServer::individualConfigs"/></desc></const>
     1844    <const name="MAC"         value="3"><desc><link to="IDHCPServer::individualConfigs"/></desc></const>
    18391845  </enum>
    18401846
    18411847  <enum
    1842     name="DHCPGroupFilterType"
    1843     uuid="0639cd66-94b7-41ef-18ac-485636e46d97"
     1848    name="DHCPGroupConditionType"
     1849    uuid="2cb9280f-ada2-4194-dee8-bfb8ad77119d"
    18441850    >
    18451851    <const name="MAC"                     value="0"><desc>MAC address</desc></const>
     
    22412247      <desc>Whether this is an inclusive or exclusive group membership condition</desc>
    22422248    </attribute>
    2243     <attribute name="type" type="DHCPGroupFilterType" readonly="no">
     2249    <attribute name="type" type="DHCPGroupConditionType" readonly="no">
    22442250      <desc>Defines how the <link to="IDHCPGroupCondition::value"/> is interpreted.</desc>
    22452251    </attribute>
     
    22772283    <method name="addCondition">
    22782284      <param name="inclusive"  dir="in" type="boolean"/>
    2279       <param name="type"       dir="in" type="DHCPGroupFilterType"/>
     2285      <param name="type"       dir="in" type="DHCPGroupConditionType"/>
    22802286      <param name="value"      dir="in" type="wstring"/>
     2287      <param name="condition"  dir="return" type="IDHCPGroupCondition"/>
    22812288    </method>
    22822289
  • trunk/src/VBox/Main/include/DHCPConfigImpl.h

    r79735 r79747  
    2323
    2424#include "DHCPGlobalConfigWrap.h"
     25#include "DHCPGroupConditionWrap.h"
    2526#include "DHCPGroupConfigWrap.h"
    2627#include "DHCPIndividualConfigWrap.h"
     
    2930
    3031class DHCPServer;
     32class DHCPGroupConfig;
    3133
    3234
     
    99101    /** @} */
    100102
    101 protected:
     103
     104public:
    102105    HRESULT             i_doWriteConfig();
    103 
    104 public:
    105106    HRESULT             i_saveSettings(settings::DHCPConfig &a_rDst);
    106107    DHCPConfigScope_T   i_getScope() const RT_NOEXCEPT { return m_enmScope; }
     
    187188
    188189/**
     190 * DHCP Group inclusion/exclusion condition.
     191 */
     192class DHCPGroupCondition : public DHCPGroupConditionWrap
     193{
     194private:
     195    /** Inclusive or exclusive condition. */
     196    bool                        m_fInclusive;
     197    /** The condition type (or how m_strValue should be interpreted). */
     198    DHCPGroupConditionType_T    m_enmType;
     199    /** The value.  Interpreted according to m_enmType. */
     200    com::Utf8Str                m_strValue;
     201    /** Pointer to the parent (weak). */
     202    DHCPGroupConfig            *m_pParent;
     203
     204public:
     205    /** @name Constructors and destructors.
     206     * @{ */
     207    DHCPGroupCondition()
     208        : m_enmType(DHCPGroupConditionType_MAC)
     209        , m_pParent(NULL)
     210    {}
     211    HRESULT FinalConstruct()
     212    {
     213        return BaseFinalConstruct();
     214    }
     215    void    FinalRelease()
     216    {
     217        uninit();
     218        BaseFinalRelease();
     219    }
     220    HRESULT initWithDefaults(DHCPGroupConfig *a_pParent, bool a_fInclusive, DHCPGroupConditionType_T a_enmType,
     221                             const com::Utf8Str a_strValue);
     222    HRESULT initWithSettings(DHCPGroupConfig *a_pParent, const settings::DHCPGroupCondition &a_rSrc);
     223    void    uninit();
     224    /** @} */
     225
     226    HRESULT i_saveSettings(settings::DHCPGroupCondition &a_rDst);
     227
     228protected:
     229    /** @name Wrapped IDHCPGroupCondition properties
     230     * @{ */
     231    HRESULT getInclusive(BOOL *aInclusive) RT_OVERRIDE;
     232    HRESULT setInclusive(BOOL aInclusive) RT_OVERRIDE;
     233    HRESULT getType(DHCPGroupConditionType_T *aType) RT_OVERRIDE;
     234    HRESULT setType(DHCPGroupConditionType_T aType) RT_OVERRIDE;
     235    HRESULT getValue(com::Utf8Str &aValue) RT_OVERRIDE;
     236    HRESULT setValue(const com::Utf8Str &aValue) RT_OVERRIDE;
     237    /** @} */
     238
     239    /** @name Wrapped IDHCPGroupCondition methods
     240     * @{ */
     241    HRESULT remove() RT_OVERRIDE;
     242    /** @} */
     243};
     244
     245
     246/**
    189247 * Group configuration.
    190248 */
    191 class DHCPGroupConfig : public VirtualBoxBase, public DHCPConfig
     249class DHCPGroupConfig : public DHCPGroupConfigWrap, public DHCPConfig
    192250{
    193     /** @todo later */
     251private:
     252    /** Group name. */
     253    com::Utf8Str                                m_strName;
     254    /** Group membership conditions.   */
     255    std::vector<ComObjPtr<DHCPGroupCondition> > m_Conditions;
     256    /** Iterator for m_Conditions. */
     257    typedef std::vector<ComObjPtr<DHCPGroupCondition> >::iterator ConditionsIterator;
     258
     259public:
     260    /** @name Constructors and destructors.
     261     * @{ */
     262    DHCPGroupConfig()
     263        : DHCPConfig(DHCPConfigScope_Group, this)
     264    { }
     265    HRESULT FinalConstruct()
     266    {
     267        return BaseFinalConstruct();
     268    }
     269    void    FinalRelease()
     270    {
     271        uninit();
     272        BaseFinalRelease();
     273    }
     274    HRESULT initWithDefaults(VirtualBox *a_pVirtualBox, DHCPServer *a_pParent, const com::Utf8Str &a_rName);
     275    HRESULT initWithSettings(VirtualBox *a_pVirtualBox, DHCPServer *a_pParent, const settings::DHCPGroupConfig &a_rSrc);
     276    void    uninit();
     277    /** @} */
     278
     279    HRESULT i_saveSettings(settings::DHCPGroupConfig &a_rDst);
     280    HRESULT i_removeCondition(DHCPGroupCondition *a_pCondition);
     281
     282protected:
     283    /** @name Wrapped IDHCPConfig properties
     284     * @{ */
     285    HRESULT getScope(DHCPConfigScope_T *aScope) RT_OVERRIDE             { return i_getScope(aScope); }
     286    HRESULT getMinLeaseTime(ULONG *aMinLeaseTime) RT_OVERRIDE           { return i_getMinLeaseTime(aMinLeaseTime); }
     287    HRESULT setMinLeaseTime(ULONG aMinLeaseTime) RT_OVERRIDE            { return i_setMinLeaseTime(aMinLeaseTime); }
     288    HRESULT getDefaultLeaseTime(ULONG *aDefaultLeaseTime) RT_OVERRIDE   { return i_getDefaultLeaseTime(aDefaultLeaseTime); }
     289    HRESULT setDefaultLeaseTime(ULONG aDefaultLeaseTime) RT_OVERRIDE    { return i_setDefaultLeaseTime(aDefaultLeaseTime); }
     290    HRESULT getMaxLeaseTime(ULONG *aMaxLeaseTime) RT_OVERRIDE           { return i_getMaxLeaseTime(aMaxLeaseTime); }
     291    HRESULT setMaxLeaseTime(ULONG aMaxLeaseTime) RT_OVERRIDE            { return i_setMaxLeaseTime(aMaxLeaseTime); }
     292    /** @} */
     293
     294    /** @name Wrapped IDHCPGroupConfig properties
     295     * @{ */
     296    HRESULT getName(com::Utf8Str &aName) RT_OVERRIDE;
     297    HRESULT setName(const com::Utf8Str &aName) RT_OVERRIDE;
     298    HRESULT getConditions(std::vector<ComPtr<IDHCPGroupCondition> > &aConditions) RT_OVERRIDE;
     299    /** @} */
     300
     301    /** @name Wrapped IDHCPConfig methods
     302     * @{ */
     303    HRESULT setOption(DhcpOpt_T aOption, DHCPOptionEncoding_T aEncoding, const com::Utf8Str &aValue) RT_OVERRIDE
     304    {
     305        return i_setOption(aOption, aEncoding, aValue);
     306    }
     307
     308    HRESULT removeOption(DhcpOpt_T aOption) RT_OVERRIDE
     309    {
     310        return i_removeOption(aOption);
     311    }
     312
     313    HRESULT removeAllOptions() RT_OVERRIDE
     314    {
     315        return i_removeAllOptions();
     316    }
     317
     318    HRESULT getOption(DhcpOpt_T aOption, DHCPOptionEncoding_T *aEncoding, com::Utf8Str &aValue) RT_OVERRIDE
     319    {
     320        return i_getOption(aOption, aEncoding, aValue);
     321    }
     322
     323    HRESULT getAllOptions(std::vector<DhcpOpt_T> &aOptions, std::vector<DHCPOptionEncoding_T> &aEncodings,
     324                          std::vector<com::Utf8Str> &aValues) RT_OVERRIDE
     325    {
     326        return i_getAllOptions(aOptions, aEncodings, aValues);
     327    }
     328    /** @} */
     329
     330    /** @name Wrapped IDHCPGroupConfig methods
     331     * @{ */
     332    HRESULT addCondition(BOOL aInclusive, DHCPGroupConditionType_T aType, const com::Utf8Str &aValue,
     333                         ComPtr<IDHCPGroupCondition> &aCondition) RT_OVERRIDE;
     334    /** @} */
    194335};
    195336
  • trunk/src/VBox/Main/src-server/DHCPConfigImpl.cpp

    r79735 r79747  
    5959    m_secMaxLeaseTime     = rConfig.secMaxLeaseTime;
    6060
    61     for (settings::DhcpOptionMap::const_iterator it = rConfig.OptionMap.begin(); it != rConfig.OptionMap.end(); ++it)
     61    for (settings::DhcpOptionMap::const_iterator it = rConfig.mapOptions.begin(); it != rConfig.mapOptions.end(); ++it)
    6262    {
    6363        try
     
    8585    try
    8686    {
    87         a_rDst.OptionMap = m_OptionMap;
     87        a_rDst.mapOptions = m_OptionMap;
    8888    }
    8989    catch (std::bad_alloc &)
     
    223223        aValues.resize(m_OptionMap.size());
    224224        size_t i = 0;
    225         for (settings::DhcpOptionMap::iterator it = m_OptionMap.begin(); it != m_OptionMap.end(); ++it)
     225        for (settings::DhcpOptionMap::iterator it = m_OptionMap.begin(); it != m_OptionMap.end(); ++it, i++)
    226226        {
    227227            aOptions[i]   = it->first;
     
    244244 *
    245245 * @note    Must hold no locks when this is called!
     246 * @note    Public because DHCPGroupCondition needs to call it too.
    246247 */
    247248HRESULT DHCPConfig::i_doWriteConfig()
     
    327328HRESULT DHCPGlobalConfig::i_saveSettings(settings::DHCPConfig &a_rDst)
    328329{
     330    AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     331
    329332    return DHCPConfig::i_saveSettings(a_rDst);
    330333}
     
    416419
    417420/*********************************************************************************************************************************
     421*   DHCPGroupCondition Implementation                                                                                            *
     422*********************************************************************************************************************************/
     423#undef  LOG_GROUP
     424#define LOG_GROUP LOG_GROUP_MAIN_DHCPGROUPCONDITION
     425
     426HRESULT DHCPGroupCondition::initWithDefaults(DHCPGroupConfig *a_pParent, bool a_fInclusive, DHCPGroupConditionType_T a_enmType,
     427                                             const com::Utf8Str a_strValue)
     428{
     429    AutoInitSpan autoInitSpan(this);
     430    AssertReturn(autoInitSpan.isOk(), E_FAIL);
     431
     432    m_pParent    = a_pParent;
     433    m_fInclusive = a_fInclusive;
     434    m_enmType    = a_enmType;
     435    HRESULT hrc = m_strValue.assignEx(a_strValue);
     436
     437    if (SUCCEEDED(hrc))
     438        autoInitSpan.setSucceeded();
     439    else
     440        autoInitSpan.setFailed(hrc);
     441    return hrc;
     442}
     443
     444
     445HRESULT DHCPGroupCondition::initWithSettings(DHCPGroupConfig *a_pParent, const settings::DHCPGroupCondition &a_rSrc)
     446{
     447    return initWithDefaults(a_pParent, a_rSrc.fInclusive, a_rSrc.enmType, a_rSrc.strValue);
     448}
     449
     450
     451void DHCPGroupCondition::uninit()
     452{
     453    AutoUninitSpan autoUninitSpan(this);
     454    if (!autoUninitSpan.uninitDone())
     455        autoUninitSpan.setSucceeded();
     456}
     457
     458
     459HRESULT DHCPGroupCondition::i_saveSettings(settings::DHCPGroupCondition &a_rDst)
     460{
     461    AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     462
     463    a_rDst.fInclusive = m_fInclusive;
     464    a_rDst.enmType    = m_enmType;
     465    return a_rDst.strValue.assignEx(m_strValue);
     466}
     467
     468
     469HRESULT DHCPGroupCondition::getInclusive(BOOL *aInclusive)
     470{
     471    AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     472    *aInclusive = m_fInclusive;
     473    return S_OK;
     474}
     475
     476
     477HRESULT DHCPGroupCondition::setInclusive(BOOL aInclusive)
     478{
     479    {
     480        AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
     481        if ((aInclusive != FALSE) == m_fInclusive)
     482            return S_OK;
     483        m_fInclusive = aInclusive != FALSE;
     484    }
     485    return m_pParent->i_doWriteConfig();
     486}
     487
     488
     489HRESULT DHCPGroupCondition::getType(DHCPGroupConditionType_T *aType)
     490{
     491    AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     492    *aType = m_enmType;
     493    return S_OK;
     494}
     495
     496
     497HRESULT DHCPGroupCondition::setType(DHCPGroupConditionType_T aType)
     498{
     499    {
     500        AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
     501        if (aType == m_enmType)
     502            return S_OK;
     503        m_enmType = aType;
     504    }
     505    return m_pParent->i_doWriteConfig();
     506}
     507
     508
     509HRESULT DHCPGroupCondition::getValue(com::Utf8Str &aValue)
     510{
     511    AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     512    return aValue.assignEx(m_strValue);
     513}
     514
     515
     516HRESULT DHCPGroupCondition::setValue(const com::Utf8Str &aValue)
     517{
     518    {
     519        AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
     520        if (aValue == m_strValue)
     521            return S_OK;
     522        HRESULT hrc = m_strValue.assignEx(aValue);
     523        if (FAILED(hrc))
     524            return hrc;
     525    }
     526    return m_pParent->i_doWriteConfig();
     527}
     528
     529
     530HRESULT DHCPGroupCondition::remove()
     531{
     532    return m_pParent->i_removeCondition(this);
     533}
     534
     535
     536
     537/*********************************************************************************************************************************
     538*   DHCPGroupConfig Implementation                                                                                               *
     539*********************************************************************************************************************************/
     540#undef  LOG_GROUP
     541#define LOG_GROUP LOG_GROUP_MAIN_DHCPGROUPCONFIG
     542
     543
     544HRESULT DHCPGroupConfig::initWithDefaults(VirtualBox *a_pVirtualBox, DHCPServer *a_pParent, const com::Utf8Str &a_rName)
     545{
     546    AutoInitSpan autoInitSpan(this);
     547    AssertReturn(autoInitSpan.isOk(), E_FAIL);
     548
     549    Assert(m_Conditions.size() == 0);
     550    HRESULT hrc = DHCPConfig::i_initWithDefaults(a_pVirtualBox, a_pParent);
     551    if (SUCCEEDED(hrc))
     552        hrc = m_strName.assignEx(a_rName);
     553
     554    if (SUCCEEDED(hrc))
     555        autoInitSpan.setSucceeded();
     556    else
     557        autoInitSpan.setFailed(hrc);
     558    return hrc;
     559}
     560
     561
     562HRESULT DHCPGroupConfig::initWithSettings(VirtualBox *a_pVirtualBox, DHCPServer *a_pParent, const settings::DHCPGroupConfig &a_rSrc)
     563{
     564    AutoInitSpan autoInitSpan(this);
     565    AssertReturn(autoInitSpan.isOk(), E_FAIL);
     566
     567    Assert(m_Conditions.size() == 0);
     568    HRESULT hrc = DHCPConfig::i_initWithSettings(a_pVirtualBox, a_pParent, a_rSrc);
     569    if (SUCCEEDED(hrc))
     570        hrc = m_strName.assignEx(a_rSrc.strName);
     571
     572    for (settings::DHCPGroupConditionVec::const_iterator it = a_rSrc.vecConditions.begin();
     573         it != a_rSrc.vecConditions.end() && SUCCEEDED(hrc); ++it)
     574    {
     575        ComObjPtr<DHCPGroupCondition> ptrCondition;
     576        hrc = ptrCondition.createObject();
     577        if (SUCCEEDED(hrc))
     578        {
     579            hrc = ptrCondition->initWithSettings(this, *it);
     580            if (SUCCEEDED(hrc))
     581            {
     582                try
     583                {
     584                    m_Conditions.push_back(ptrCondition);
     585                }
     586                catch (std::bad_alloc &)
     587                {
     588                    hrc = E_OUTOFMEMORY;
     589                }
     590            }
     591        }
     592    }
     593
     594    if (SUCCEEDED(hrc))
     595        autoInitSpan.setSucceeded();
     596    else
     597        autoInitSpan.setFailed(hrc);
     598    return hrc;
     599}
     600
     601
     602void    DHCPGroupConfig::uninit()
     603{
     604    AutoUninitSpan autoUninitSpan(this);
     605    if (!autoUninitSpan.uninitDone())
     606        autoUninitSpan.setSucceeded();
     607}
     608
     609
     610HRESULT DHCPGroupConfig::i_saveSettings(settings::DHCPGroupConfig &a_rDst)
     611{
     612    AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     613
     614    HRESULT hrc = DHCPConfig::i_saveSettings(a_rDst);
     615    if (SUCCEEDED(hrc))
     616        hrc = a_rDst.strName.assignEx(m_strName);
     617    if (SUCCEEDED(hrc))
     618    {
     619        size_t const cConditions = m_Conditions.size();
     620        try
     621        {
     622            a_rDst.vecConditions.resize(cConditions);
     623        }
     624        catch (std::bad_alloc &)
     625        {
     626            hrc = E_OUTOFMEMORY;
     627        }
     628
     629        for (size_t i = 0; i < cConditions && SUCCEEDED(hrc); i++)
     630            hrc = m_Conditions[i]->i_saveSettings(a_rDst.vecConditions[i]);
     631    }
     632    return hrc;
     633}
     634
     635
     636HRESULT DHCPGroupConfig::i_removeCondition(DHCPGroupCondition *a_pCondition)
     637{
     638    AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
     639
     640    for (ConditionsIterator it = m_Conditions.begin(); it != m_Conditions.end();)
     641    {
     642        DHCPGroupCondition *pCurCondition = *it;
     643        if (pCurCondition == a_pCondition)
     644            it = m_Conditions.erase(it);
     645        else
     646            ++it;
     647    }
     648
     649    /* Never mind if already delete, right? */
     650    return S_OK;
     651}
     652
     653
     654HRESULT DHCPGroupConfig::getName(com::Utf8Str &aName)
     655{
     656    AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     657    return aName.assignEx(m_strName);
     658}
     659
     660
     661HRESULT DHCPGroupConfig::setName(const com::Utf8Str &aName)
     662{
     663    {
     664        AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
     665        if (aName == m_strName)
     666            return S_OK;
     667        HRESULT hrc = m_strName.assignEx(aName);
     668        if (FAILED(hrc))
     669            return hrc;
     670    }
     671    return i_doWriteConfig();
     672}
     673
     674
     675HRESULT DHCPGroupConfig::getConditions(std::vector<ComPtr<IDHCPGroupCondition> > &aConditions)
     676{
     677    AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     678    size_t const cConditions = m_Conditions.size();
     679    try
     680    {
     681        aConditions.resize(cConditions);
     682    }
     683    catch (std::bad_alloc &)
     684    {
     685        return E_OUTOFMEMORY;
     686    }
     687    HRESULT hrc = S_OK;
     688    for (size_t i = 0; i < cConditions && SUCCEEDED(hrc); i++)
     689        hrc = m_Conditions[i].queryInterfaceTo(aConditions[i].asOutParam());
     690    return hrc;
     691}
     692
     693
     694HRESULT DHCPGroupConfig::addCondition(BOOL aInclusive, DHCPGroupConditionType_T aType, const com::Utf8Str &aValue,
     695                                      ComPtr<IDHCPGroupCondition> &aCondition)
     696{
     697    ComObjPtr<DHCPGroupCondition> ptrCondition;
     698    HRESULT hrc = ptrCondition.createObject();
     699    if (SUCCEEDED(hrc))
     700        hrc = ptrCondition->initWithDefaults(this, aInclusive != FALSE, aType, aValue);
     701    if (SUCCEEDED(hrc))
     702    {
     703        hrc = ptrCondition.queryInterfaceTo(aCondition.asOutParam());
     704        if (SUCCEEDED(hrc))
     705        {
     706            AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
     707            try
     708            {
     709                m_Conditions.push_back(ptrCondition);
     710            }
     711            catch (std::bad_alloc &)
     712            {
     713                aCondition.setNull();
     714                return E_OUTOFMEMORY;
     715            }
     716        }
     717    }
     718
     719    return hrc;
     720}
     721
     722
     723
     724/*********************************************************************************************************************************
    418725*   DHCPIndividualConfig Implementation                                                                                          *
    419726*********************************************************************************************************************************/
     
    510817HRESULT DHCPIndividualConfig::i_saveSettings(settings::DHCPIndividualConfig &a_rDst)
    511818{
     819    AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     820
    512821    a_rDst.uSlot = m_uSlot;
    513822    int vrc = a_rDst.strMACAddress.printfNoThrow("%RTmac", &m_MACAddress);
     
    536845
    537846    /* Format the return string: */
    538     int vrc = aMACAddress.printfNoThrow("%RTmac", &m_MACAddress);
     847    int vrc = aMACAddress.printfNoThrow("%RTmac", &MACAddress);
    539848    return RT_SUCCESS(vrc) ? S_OK : E_OUTOFMEMORY;
    540849}
     
    619928                    hrc = S_OK;
    620929                else
    621                     hrc = setError(hrc, tr("INetworkAdapter returned bogus MAC address '%ls'"), bstrMACAddress.raw());
     930                    hrc = setErrorBoth(E_FAIL, vrc, tr("INetworkAdapter returned bogus MAC address '%ls': %Rrc"),
     931                                       bstrMACAddress.raw(), vrc);
    622932            }
    623933        }
  • trunk/src/VBox/Main/src-server/DHCPServerImpl.cpp

    r79740 r79747  
    6666    {}
    6767
    68     static const char * const kDsrKeyGateway;
    69     static const char * const kDsrKeyLowerIp;
    70     static const char * const kDsrKeyUpperIp;
    7168    static const char * const kDsrKeyConfig;
    7269    static const char * const kDsrKeyComment;
    7370};
    7471
    75 /*static*/ const char * const DHCPServerRunner::kDsrKeyGateway = "--gateway";
    76 /*static*/ const char * const DHCPServerRunner::kDsrKeyLowerIp = "--lower-ip";
    77 /*static*/ const char * const DHCPServerRunner::kDsrKeyUpperIp = "--upper-ip";
    7872/*static*/ const char * const DHCPServerRunner::kDsrKeyConfig  = "--config";
    7973/*static*/ const char * const DHCPServerRunner::kDsrKeyComment = "--comment";
     
    8983        , strName()
    9084        , enabled(FALSE)
    91 //        , router(false)
    9285        , uIndividualMACAddressVersion(1)
    9386    {
     
    10699
    107100    BOOL enabled;
    108 #if 0
    109     /** Don't quit get WTF this is about, but the old addOption method contained the
    110      * following hint: "Indirect way to understand that we're on NAT network."
    111      *
    112      * Apparently this is a busted with the new dhcpd implementation, so we don't
    113      * maintain it with the API overhaul in 6.0.12.
    114      */
    115     bool router;
    116 #endif
    117101    DHCPServerRunner dhcp;
    118102
     
    126110    ComObjPtr<DHCPGlobalConfig> globalConfig;
    127111
    128 //    /** Group configuration indexed by name. */
    129 //    std::map<com::Utf8Str, ComObjPtr<DHCPGroupConfig>> groupConfigs;
    130 //    /** Iterator for groupConfigs. */
    131 //    typedef std::map<com::Utf8Str, ComObjPtr<DHCPGroupConfig>>::iterator GroupConfigIterator;
     112    /** Group configuration indexed by name. */
     113    std::map<com::Utf8Str, ComObjPtr<DHCPGroupConfig>> groupConfigs;
     114    /** Iterator for groupConfigs. */
     115    typedef std::map<com::Utf8Str, ComObjPtr<DHCPGroupConfig>>::iterator GroupConfigIterator;
    132116
    133117    /** Individual (host) configuration indexed by MAC address or VM UUID. */
     
    210194    if (SUCCEEDED(hrc))
    211195        hrc = m->globalConfig->initWithDefaults(aVirtualBox, this);
     196
     197    Assert(m->groupConfigs.size() == 0);
     198    Assert(m->individualConfigs.size() == 0);
    212199
    213200    /* Confirm a successful initialization or not: */
     
    240227    HRESULT hrc = m->globalConfig.createObject();
    241228    if (SUCCEEDED(hrc))
    242         hrc = m->globalConfig->initWithSettings(aVirtualBox, this, rData.GlobalConfig);
     229        hrc = m->globalConfig->initWithSettings(aVirtualBox, this, rData.globalConfig);
    243230
    244231    /*
    245232     * Group configurations:
    246233     */
     234    Assert(m->groupConfigs.size() == 0);
     235    for (settings::DHCPGroupConfigVec::const_iterator it = rData.vecGroupConfigs.begin();
     236         it != rData.vecGroupConfigs.end() && SUCCEEDED(hrc); ++it)
     237    {
     238        ComObjPtr<DHCPGroupConfig> ptrGroupConfig;
     239        hrc = ptrGroupConfig.createObject();
     240        if (SUCCEEDED(hrc))
     241            hrc = ptrGroupConfig->initWithSettings(aVirtualBox, this, *it);
     242        if (SUCCEEDED(hrc))
     243        {
     244            try
     245            {
     246                m->groupConfigs[it->strName] = ptrGroupConfig;
     247            }
     248            catch (std::bad_alloc &)
     249            {
     250                return E_OUTOFMEMORY;
     251            }
     252        }
     253    }
    247254
    248255    /*
     
    250257     */
    251258    Assert(m->individualConfigs.size() == 0);
    252     if (SUCCEEDED(hrc))
    253     {
    254         for (settings::DHCPIndividualConfigMap::const_iterator it = rData.IndividualConfigs.begin();
    255              it != rData.IndividualConfigs.end() && SUCCEEDED(hrc); ++it)
    256         {
    257             ComObjPtr<DHCPIndividualConfig> ptrIndiCfg;
    258             com::Utf8Str                    strKey;
    259             if (!it->second.strVMName.isNotEmpty())
     259    for (settings::DHCPIndividualConfigMap::const_iterator it = rData.mapIndividualConfigs.begin();
     260         it != rData.mapIndividualConfigs.end() && SUCCEEDED(hrc); ++it)
     261    {
     262        ComObjPtr<DHCPIndividualConfig> ptrIndiCfg;
     263        com::Utf8Str                    strKey;
     264        if (!it->second.strVMName.isNotEmpty())
     265        {
     266            RTMAC MACAddress;
     267            int vrc = RTNetStrToMacAddr(it->second.strMACAddress.c_str(), &MACAddress);
     268            if (RT_FAILURE(vrc))
    260269            {
    261                 RTMAC MACAddress;
    262                 int vrc = RTNetStrToMacAddr(it->second.strMACAddress.c_str(), &MACAddress);
    263                 if (RT_FAILURE(vrc))
    264                 {
    265                     LogRel(("Ignoring invalid MAC address for individual DHCP config: '%s' - %Rrc\n", it->second.strMACAddress.c_str(), vrc));
    266                     continue;
    267                 }
    268 
    269                 vrc = strKey.printfNoThrow("%RTmac", &MACAddress);
    270                 AssertRCReturn(vrc, E_OUTOFMEMORY);
    271 
     270                LogRel(("Ignoring invalid MAC address for individual DHCP config: '%s' - %Rrc\n", it->second.strMACAddress.c_str(), vrc));
     271                continue;
     272            }
     273
     274            vrc = strKey.printfNoThrow("%RTmac", &MACAddress);
     275            AssertRCReturn(vrc, E_OUTOFMEMORY);
     276
     277            hrc = ptrIndiCfg.createObject();
     278            if (SUCCEEDED(hrc))
     279                hrc = ptrIndiCfg->initWithSettingsAndMACAddress(aVirtualBox, this, it->second, &MACAddress);
     280        }
     281        else
     282        {
     283            /* This ASSUMES that we're being called after the machines have been
     284               loaded so we can resolve VM names into UUID for old settings. */
     285            com::Guid idMachine;
     286            hrc = i_vmNameToIdAndValidateSlot(it->second.strVMName, it->second.uSlot, idMachine);
     287            if (SUCCEEDED(hrc))
     288            {
    272289                hrc = ptrIndiCfg.createObject();
    273290                if (SUCCEEDED(hrc))
    274                     hrc = ptrIndiCfg->initWithSettingsAndMACAddress(aVirtualBox, this, it->second, &MACAddress);
     291                    hrc = ptrIndiCfg->initWithSettingsAndMachineIdAndSlot(aVirtualBox, this, it->second,
     292                                                                          idMachine, it->second.uSlot,
     293                                                                          m->uIndividualMACAddressVersion - UINT32_MAX / 4);
    275294            }
    276             else
     295        }
     296        if (SUCCEEDED(hrc))
     297        {
     298            try
    277299            {
    278                 /* This ASSUMES that we're being called after the machines have been
    279                    loaded so we can resolve VM names into UUID for old settings. */
    280                 com::Guid idMachine;
    281                 hrc = i_vmNameToIdAndValidateSlot(it->second.strVMName, it->second.uSlot, idMachine);
    282                 if (SUCCEEDED(hrc))
    283                 {
    284                     hrc = ptrIndiCfg.createObject();
    285                     if (SUCCEEDED(hrc))
    286                         hrc = ptrIndiCfg->initWithSettingsAndMachineIdAndSlot(aVirtualBox, this, it->second,
    287                                                                               idMachine, it->second.uSlot,
    288                                                                               m->uIndividualMACAddressVersion - UINT32_MAX / 4);
    289                 }
     300                m->individualConfigs[strKey] = ptrIndiCfg;
    290301            }
    291             if (SUCCEEDED(hrc))
     302            catch (std::bad_alloc &)
    292303            {
    293                 try
    294                 {
    295                     m->individualConfigs[strKey] = ptrIndiCfg;
    296                 }
    297                 catch (std::bad_alloc &)
    298                 {
    299                     return E_OUTOFMEMORY;
    300                 }
     304                return E_OUTOFMEMORY;
    301305            }
    302306        }
     
    326330
    327331    /* Global configuration: */
    328     HRESULT hrc = m->globalConfig->i_saveSettings(rData.GlobalConfig);
     332    HRESULT hrc = m->globalConfig->i_saveSettings(rData.globalConfig);
    329333
    330334    /* Group configuration: */
     335    size_t const cGroupConfigs = m->groupConfigs.size();
     336    try
     337    {
     338        rData.vecGroupConfigs.resize(cGroupConfigs);
     339    }
     340    catch (std::bad_alloc &)
     341    {
     342        return E_OUTOFMEMORY;
     343    }
     344    size_t i = 0;
     345    for (Data::GroupConfigIterator it = m->groupConfigs.begin(); it != m->groupConfigs.end() && SUCCEEDED(hrc); ++it, i++)
     346    {
     347        try
     348        {
     349            rData.vecGroupConfigs[i] = settings::DHCPGroupConfig();
     350        }
     351        catch (std::bad_alloc &)
     352        {
     353            return E_OUTOFMEMORY;
     354        }
     355        hrc = it->second->i_saveSettings(rData.vecGroupConfigs[i]);
     356    }
    331357
    332358    /* Individual configuration: */
     
    336362        try
    337363        {
    338             rData.IndividualConfigs[it->first] = settings::DHCPIndividualConfig();
     364            rData.mapIndividualConfigs[it->first] = settings::DHCPIndividualConfig();
    339365        }
    340366        catch (std::bad_alloc &)
     
    342368            return E_OUTOFMEMORY;
    343369        }
    344         hrc = it->second->i_saveSettings(rData.IndividualConfigs[it->first]);
     370        hrc = it->second->i_saveSettings(rData.mapIndividualConfigs[it->first]);
    345371    }
    346372
     
    681707
    682708
     709/**
     710 * Validates the VM name and slot, returning the machine ID.
     711 *
     712 * If a machine ID is given instead of a name, we won't check whether it
     713 * actually exists...
     714 *
     715 * @returns COM status code.
     716 * @param   aVmName             The VM name or UUID.
     717 * @param   aSlot               The slot.
     718 * @param   idMachine           Where to return the VM UUID.
     719 */
    683720HRESULT DHCPServer::i_vmNameToIdAndValidateSlot(const com::Utf8Str &aVmName, LONG aSlot, com::Guid &idMachine)
    684721{
     
    692729        /* No, find the VM and get it's UUID. */
    693730        ComObjPtr<Machine> ptrMachine;
    694         HRESULT hrc = m->pVirtualBox->i_findMachine(aVmName, false /*fPermitInaccessible*/, true /*aSetError*/, &ptrMachine);
     731        HRESULT hrc = m->pVirtualBox->i_findMachineByName(aVmName, true /*aSetError*/, &ptrMachine);
    695732        if (SUCCEEDED(hrc))
    696733            idMachine = ptrMachine->i_getId();
     
    856893{
    857894    AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
    858 #if 0 /** @todo implement group configs   */
    859 
     895
     896    size_t const cGroupConfigs = m->groupConfigs.size();
    860897    try
    861898    {
    862         aGroupConfigs.resize(m->groupConfigs.size());
     899        aGroupConfigs.resize(cGroupConfigs);
    863900    }
    864901    catch (std::bad_alloc &)
     
    868905
    869906    size_t i = 0;
    870     for (Data::GroupConfigIterator it = m->groupConfigs.begin(); it != m->groupConfigs.end(); ++it)
    871     {
     907    for (Data::GroupConfigIterator it = m->groupConfigs.begin(); it != m->groupConfigs.end(); ++it, i++)
     908    {
     909        Assert(i < cGroupConfigs);
    872910        HRESULT hrc = it->second.queryInterfaceTo(aGroupConfigs[i].asOutParam());
    873911        if (FAILED(hrc))
     
    875913    }
    876914
    877 #else
    878     aGroupConfigs.resize(0);
    879 #endif
    880915    return S_OK;
    881916}
     
    886921    AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
    887922
     923    size_t const cIndividualConfigs = m->individualConfigs.size();
    888924    try
    889925    {
    890         aIndividualConfigs.resize(m->individualConfigs.size());
     926        aIndividualConfigs.resize(cIndividualConfigs);
    891927    }
    892928    catch (std::bad_alloc &)
     
    896932
    897933    size_t i = 0;
    898     for (Data::IndividualConfigIterator it = m->individualConfigs.begin(); it != m->individualConfigs.end(); ++it)
    899     {
     934    for (Data::IndividualConfigIterator it = m->individualConfigs.begin(); it != m->individualConfigs.end(); ++it, i++)
     935    {
     936        Assert(i < cIndividualConfigs);
    900937        HRESULT hrc = it->second.queryInterfaceTo(aIndividualConfigs[i].asOutParam());
    901938        if (FAILED(hrc))
     
    957994         * Groups.
    958995         */
    959         //for (Data::GroupConfigIterator it = m->groupConfigs.begin(); it != m->groupConfigs.end(); ++it)
    960         //    it->second->i_writeDhcpdConfig(pElmRoot->createChild("Config"));
     996        for (Data::GroupConfigIterator it = m->groupConfigs.begin(); it != m->groupConfigs.end(); ++it)
     997            it->second->i_writeDhcpdConfig(pElmRoot->createChild("Group"));
    961998
    962999        /*
     
    12671304            if (aName.isNotEmpty())
    12681305                return setError(E_INVALIDARG, tr("The name must be empty or NULL for the Global scope!"));
     1306
    12691307            /* No locking required here. */
    12701308            return m->globalConfig.queryInterfaceTo(aConfig.asOutParam());
    12711309
    12721310        case DHCPConfigScope_Group:
    1273             return setError(E_NOTIMPL, tr("Groups are not yet implemented, sorry."));
     1311        {
     1312            if (aName.isEmpty())
     1313                return setError(E_INVALIDARG, tr("A group must have a name!"));
     1314            if (aName.length() > _1K)
     1315                return setError(E_INVALIDARG, tr("Name too long! %zu bytes"), aName.length());
     1316
     1317            /* Look up the group: */
     1318            {
     1319                AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     1320                Data::GroupConfigIterator it = m->groupConfigs.find(aName);
     1321                if (it != m->groupConfigs.end())
     1322                    return it->second.queryInterfaceTo(aConfig.asOutParam());
     1323            }
     1324            /* Create a new group if we can. */
     1325            if (!aMayAdd)
     1326                return setError(VBOX_E_OBJECT_NOT_FOUND, tr("Found no configuration for group %s"), aName.c_str());
     1327            ComObjPtr<DHCPGroupConfig> ptrGroupConfig;
     1328            HRESULT hrc = ptrGroupConfig.createObject();
     1329            if (SUCCEEDED(hrc))
     1330                hrc = ptrGroupConfig->initWithDefaults(m->pVirtualBox, this, aName);
     1331            if (SUCCEEDED(hrc))
     1332            {
     1333                AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
     1334
     1335                /* Check for insertion race: */
     1336                Data::GroupConfigIterator it = m->groupConfigs.find(aName);
     1337                if (it != m->groupConfigs.end())
     1338                    return it->second.queryInterfaceTo(aConfig.asOutParam()); /* creation race*/
     1339
     1340                /* Try insert it: */
     1341                try
     1342                {
     1343                    m->groupConfigs[aName] = ptrGroupConfig;
     1344                }
     1345                catch (std::bad_alloc &)
     1346                {
     1347                    return E_OUTOFMEMORY;
     1348                }
     1349                return ptrGroupConfig.queryInterfaceTo(aConfig.asOutParam());
     1350            }
     1351            return hrc;
     1352        }
    12741353
    12751354        case DHCPConfigScope_MachineNIC:
  • trunk/src/VBox/Main/xml/Settings.cpp

    r79736 r79747  
    16291629}
    16301630
    1631 
    16321631/**
    16331632 * Default constructor.
    16341633 */
     1634DHCPGroupCondition::DHCPGroupCondition()
     1635    : fInclusive(true)
     1636    , enmType(DHCPGroupConditionType_MAC)
     1637    , strValue()
     1638{
     1639}
     1640
     1641/**
     1642 * Default constructor.
     1643 */
    16351644DHCPConfig::DHCPConfig()
    1636     : OptionMap()
     1645    : mapOptions()
    16371646    , secMinLeaseTime(0)
    16381647    , secDefaultLeaseTime(0)
    16391648    , secMaxLeaseTime(0)
     1649{
     1650}
     1651
     1652/**
     1653 * Default constructor.
     1654 */
     1655DHCPGroupConfig::DHCPGroupConfig()
     1656    : DHCPConfig()
     1657    , strName()
     1658    , vecConditions()
    16401659{
    16411660}
     
    17191738        pElmThis->setAttribute("networkName", srv.strNetworkName);
    17201739        pElmThis->setAttribute("IPAddress", srv.strIPAddress);
    1721         DhcpOptConstIterator itOpt = srv.GlobalConfig.OptionMap.find(DhcpOpt_SubnetMask);
    1722         if (itOpt != srv.GlobalConfig.OptionMap.end())
     1740        DhcpOptConstIterator itOpt = srv.globalConfig.mapOptions.find(DhcpOpt_SubnetMask);
     1741        if (itOpt != srv.globalConfig.mapOptions.end())
    17231742            pElmThis->setAttribute("networkMask", itOpt->second.strValue);
    17241743        pElmThis->setAttribute("lowerIP", srv.strIPLower);
     
    17271746
    17281747        /* We don't want duplicate validation check of networkMask here*/
    1729         if (srv.GlobalConfig.OptionMap.size() > (itOpt != srv.GlobalConfig.OptionMap.end() ? 1U : 0U))
     1748        if (srv.globalConfig.mapOptions.size() > (itOpt != srv.globalConfig.mapOptions.end() ? 1U : 0U))
    17301749        {
    17311750            xml::ElementNode *pElmOptions = pElmThis->createChild("Options");
    1732             buildDHCPOptions(*pElmOptions, srv.GlobalConfig, true);
    1733         }
    1734 
    1735         if (srv.IndividualConfigs.size() > 0)
    1736         {
    1737             for (DHCPIndividualConfigMap::const_iterator itHost = srv.IndividualConfigs.begin();
    1738                  itHost != srv.IndividualConfigs.end(); ++itHost)
    1739             {
    1740                 DHCPIndividualConfig const &rIndividualConfig = itHost->second;
    1741 
    1742                 xml::ElementNode *pElmConfig = pElmThis->createChild("Config");
    1743                 if (rIndividualConfig.strMACAddress.isNotEmpty())
    1744                     pElmConfig->setAttribute("MACAddress", rIndividualConfig.strMACAddress);
    1745                 if (rIndividualConfig.strVMName.isNotEmpty())
    1746                     pElmConfig->setAttribute("vm-name", rIndividualConfig.strVMName);
    1747                 if (rIndividualConfig.uSlot != 0 || rIndividualConfig.strVMName.isNotEmpty())
    1748                     pElmConfig->setAttribute("slot", rIndividualConfig.strVMName);
    1749                 if (rIndividualConfig.strFixedAddress.isNotEmpty())
    1750                     pElmConfig->setAttribute("fixedAddress", rIndividualConfig.strFixedAddress);
    1751                 buildDHCPOptions(*pElmConfig, rIndividualConfig, false);
    1752             }
     1751            buildDHCPOptions(*pElmOptions, srv.globalConfig, true);
     1752        }
     1753
     1754        for (DHCPGroupConfigVec::const_iterator itGroup = srv.vecGroupConfigs.begin();
     1755             itGroup != srv.vecGroupConfigs.end(); ++itGroup)
     1756        {
     1757            DHCPGroupConfig const &rGroupConfig = *itGroup;
     1758
     1759            xml::ElementNode *pElmGroup = pElmThis->createChild("Group");
     1760            pElmGroup->setAttribute("name", rGroupConfig.strName);
     1761            buildDHCPOptions(*pElmGroup, rGroupConfig, false);
     1762
     1763            for (DHCPGroupConditionVec::const_iterator itCond = rGroupConfig.vecConditions.begin();
     1764                 itCond != rGroupConfig.vecConditions.end(); ++itCond)
     1765            {
     1766                xml::ElementNode *pElmCondition = pElmGroup->createChild("Condition");
     1767                pElmCondition->setAttribute("inclusive", itCond->fInclusive);
     1768                pElmCondition->setAttribute("type", (int32_t)itCond->enmType);
     1769                pElmCondition->setAttribute("value", itCond->strValue);
     1770            }
     1771        }
     1772
     1773        for (DHCPIndividualConfigMap::const_iterator itHost = srv.mapIndividualConfigs.begin();
     1774             itHost != srv.mapIndividualConfigs.end(); ++itHost)
     1775        {
     1776            DHCPIndividualConfig const &rIndividualConfig = itHost->second;
     1777
     1778            xml::ElementNode *pElmConfig = pElmThis->createChild("Config");
     1779            if (rIndividualConfig.strMACAddress.isNotEmpty())
     1780                pElmConfig->setAttribute("MACAddress", rIndividualConfig.strMACAddress);
     1781            if (rIndividualConfig.strVMName.isNotEmpty())
     1782                pElmConfig->setAttribute("vm-name", rIndividualConfig.strVMName);
     1783            if (rIndividualConfig.uSlot != 0 || rIndividualConfig.strVMName.isNotEmpty())
     1784                pElmConfig->setAttribute("slot", rIndividualConfig.uSlot);
     1785            if (rIndividualConfig.strFixedAddress.isNotEmpty())
     1786                pElmConfig->setAttribute("fixedAddress", rIndividualConfig.strFixedAddress);
     1787            buildDHCPOptions(*pElmConfig, rIndividualConfig, false);
    17531788        }
    17541789     }
     
    17691804
    17701805    /* The DHCP options are <Option> child elements: */
    1771     for (DhcpOptConstIterator it = rConfig.OptionMap.begin(); it != rConfig.OptionMap.end(); ++it)
     1806    for (DhcpOptConstIterator it = rConfig.mapOptions.begin(); it != rConfig.mapOptions.end(); ++it)
    17721807        if (it->first != DhcpOpt_SubnetMask || !fSkipSubnetMask)
    17731808        {
     
    17951830            if (   pelmServer->getAttributeValue("networkName", srv.strNetworkName)
    17961831                && pelmServer->getAttributeValue("IPAddress", srv.strIPAddress)
    1797                 && pelmServer->getAttributeValue("networkMask", srv.GlobalConfig.OptionMap[DhcpOpt_SubnetMask].strValue)
     1832                && pelmServer->getAttributeValue("networkMask", srv.globalConfig.mapOptions[DhcpOpt_SubnetMask].strValue)
    17981833                && pelmServer->getAttributeValue("lowerIP", srv.strIPLower)
    17991834                && pelmServer->getAttributeValue("upperIP", srv.strIPUpper)
     
    18041839                xml::NodesLoop          nlOptions(*pelmServer, "Options");
    18051840                while ((pElmOptions = nlOptions.forAllNodes()) != NULL) /** @todo this loop makes no sense, there can only be one \<Options\> child. */
    1806                     readDHCPOptions(srv.GlobalConfig, *pElmOptions, true /*fIgnoreSubnetMask*/);
     1841                    readDHCPOptions(srv.globalConfig, *pElmOptions, true /*fIgnoreSubnetMask*/);
     1842
     1843                /* Group configurations: */
     1844                xml::NodesLoop nlGroup(*pelmServer, "Group");
     1845                const xml::ElementNode *pElmGroup;
     1846                size_t i = 0;
     1847                while ((pElmGroup = nlGroup.forAllNodes()) != NULL)
     1848                {
     1849                    srv.vecGroupConfigs.push_back(DHCPGroupConfig());
     1850                    DHCPGroupConfig &rGroupConfig = srv.vecGroupConfigs.back();
     1851
     1852                    if (!pElmGroup->getAttributeValue("name", rGroupConfig.strName))
     1853                        rGroupConfig.strName.printf("Unamed Group #%u", ++i);
     1854
     1855                    readDHCPOptions(rGroupConfig, *pElmGroup, false /*fIgnoreSubnetMask*/);
     1856
     1857                    xml::NodesLoop nlCondition(*pElmGroup, "Condition");
     1858                    const xml::ElementNode *pElmCondition;
     1859                    while ((pElmCondition = nlCondition.forAllNodes()) != NULL)
     1860                    {
     1861                        rGroupConfig.vecConditions.push_back(DHCPGroupCondition());
     1862                        DHCPGroupCondition &rGroupCondition = rGroupConfig.vecConditions.back();
     1863
     1864                        if (!pElmCondition->getAttributeValue("inclusive", rGroupCondition.fInclusive))
     1865                            rGroupCondition.fInclusive = true;
     1866
     1867                        int32_t iType;
     1868                        if (!pElmCondition->getAttributeValue("type", iType))
     1869                            iType = DHCPGroupConditionType_MAC;
     1870                        rGroupCondition.enmType = (DHCPGroupConditionType_T)iType;
     1871
     1872                        pElmCondition->getAttributeValue("value", rGroupCondition.strValue);
     1873                    }
     1874                }
    18071875
    18081876                /* host specific configuration: */
     
    18291897                        strKey.printf("%s/%u", strMACAddress.c_str(), uSlot);
    18301898
    1831                     DHCPIndividualConfig &rIndividualConfig = srv.IndividualConfigs[strKey];
     1899                    DHCPIndividualConfig &rIndividualConfig = srv.mapIndividualConfigs[strKey];
    18321900                    rIndividualConfig.strMACAddress = strMACAddress;
    18331901                    rIndividualConfig.strVMName     = strVMName;
     
    18371905                    readDHCPOptions(rIndividualConfig, *pElmConfig, false /*fIgnoreSubnetMask*/);
    18381906                }
     1907
    18391908                llDhcpServers.push_back(srv);
    18401909            }
     
    18641933    while ((pElmOption = nl2.forAllNodes()) != NULL)
    18651934    {
    1866         DhcpOpt_T OptName;
    1867         pElmOption->getAttributeValue("name", (uint32_t&)OptName);
     1935        int32_t iOptName;
     1936        if (!pElmOption->getAttributeValue("name", iOptName))
     1937            continue;
     1938        DhcpOpt_T OptName = (DhcpOpt_T)iOptName;
    18681939        if (OptName == DhcpOpt_SubnetMask && fIgnoreSubnetMask)
    18691940            continue;
     
    18761947            iOptEnc = DHCPOptionEncoding_Legacy;
    18771948
    1878         rConfig.OptionMap[OptName] = DhcpOptValue(strValue, (DHCPOptionEncoding_T)iOptEnc);
     1949        rConfig.mapOptions[OptName] = DhcpOptValue(strValue, (DHCPOptionEncoding_T)iOptEnc);
    18791950    } /* end of forall("Option") */
    18801951
     
    21872258#endif
    21882259        srv.strIPAddress = "192.168.56.100";
    2189         srv.GlobalConfig.OptionMap[DhcpOpt_SubnetMask] = DhcpOptValue("255.255.255.0");
     2260        srv.globalConfig.mapOptions[DhcpOpt_SubnetMask] = DhcpOptValue("255.255.255.0");
    21902261        srv.strIPLower = "192.168.56.101";
    21912262        srv.strIPUpper = "192.168.56.254";
  • trunk/src/VBox/Runtime/common/net/macstr.cpp

    r76553 r79747  
    5151{
    5252    /*
     53     * First check if it might be a 12 xdigit string without any separators.
     54     */
     55    size_t cchValue = strlen(pszValue);
     56    if (cchValue >= 12 && memchr(pszValue, ':', 12) == NULL)
     57    {
     58        bool fOkay = true;
     59        for (size_t off = 0; off < 12 && fOkay; off++)
     60            fOkay = RT_C_IS_XDIGIT(pszValue[off]);
     61        if (fOkay && cchValue > 12)
     62            for (size_t off = 12; off < cchValue && fOkay; off++)
     63                fOkay = RT_C_IS_SPACE(pszValue[off]);
     64        if (fOkay)
     65        {
     66            int rc = RTStrConvertHexBytes(pszValue, pAddr, sizeof(*pAddr), 0);
     67            if (RT_SUCCESS(rc))
     68                rc = VINF_SUCCESS;
     69            return rc;
     70        }
     71    }
     72
     73    /*
    5374     * Not quite sure if I should accept stuff like "08::27:::1" here...
    5475     * The code is accepting "::" patterns now, except for for the first
Note: See TracChangeset for help on using the changeset viewer.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette