VirtualBox

source: vbox/trunk/src/VBox/Main/src-server/NATEngineImpl.cpp@ 42699

Last change on this file since 42699 was 42551, checked in by vboxsync, 12 years ago

Main: big API naming cleanup, use all caps acronyms everywhere, including SDK docs
Frontends/VBoxManage: implement guestcontrol execute for new API, disabled by default

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 18.6 KB
Line 
1/* $Id: NATEngineImpl.cpp 42551 2012-08-02 16:44:39Z vboxsync $ */
2/** @file
3 * Implementation of INATEngine in VBoxSVC.
4 */
5
6/*
7 * Copyright (C) 2010-2012 Oracle Corporation
8 *
9 * This file is part of VirtualBox Open Source Edition (OSE), as
10 * available from http://www.virtualbox.org. This file is free software;
11 * you can redistribute it and/or modify it under the terms of the GNU
12 * General Public License (GPL) as published by the Free Software
13 * Foundation, in version 2 as it comes in the "COPYING" file of the
14 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
15 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
16 */
17
18#include "NATEngineImpl.h"
19#include "AutoCaller.h"
20#include "Logging.h"
21#include "MachineImpl.h"
22#include "GuestOSTypeImpl.h"
23
24#include <iprt/string.h>
25#include <iprt/cpp/utils.h>
26
27#include <VBox/err.h>
28#include <VBox/settings.h>
29
30
31// constructor / destructor
32////////////////////////////////////////////////////////////////////////////////
33
34NATEngine::NATEngine():mParent(NULL), mAdapter(NULL){}
35NATEngine::~NATEngine(){}
36
37HRESULT NATEngine::FinalConstruct()
38{
39 return S_OK;
40}
41
42HRESULT NATEngine::init(Machine *aParent, INetworkAdapter *aAdapter)
43{
44 AutoInitSpan autoInitSpan(this);
45 AssertReturn(autoInitSpan.isOk(), E_FAIL);
46 autoInitSpan.setSucceeded();
47 m_fModified = false;
48 mData.allocate();
49 mData->mNetwork.setNull();
50 mData->mBindIP.setNull();
51 unconst(mParent) = aParent;
52 unconst(mAdapter) = aAdapter;
53 return S_OK;
54}
55
56HRESULT NATEngine::init(Machine *aParent, INetworkAdapter *aAdapter, NATEngine *aThat)
57{
58 AutoInitSpan autoInitSpan(this);
59 AssertReturn(autoInitSpan.isOk(), E_FAIL);
60 Log(("init that:%p this:%p\n", aThat, this));
61
62 AutoCaller thatCaller(aThat);
63 AssertComRCReturnRC(thatCaller.rc());
64
65 AutoReadLock thatLock(aThat COMMA_LOCKVAL_SRC_POS);
66
67 mData.share(aThat->mData);
68 NATRuleMap::iterator it;
69 mNATRules.clear();
70 for (it = aThat->mNATRules.begin(); it != aThat->mNATRules.end(); ++it)
71 {
72 mNATRules.insert(std::make_pair(it->first, it->second));
73 }
74 unconst(mParent) = aParent;
75 unconst(mAdapter) = aAdapter;
76 unconst(mPeer) = aThat;
77 autoInitSpan.setSucceeded();
78 return S_OK;
79}
80
81HRESULT NATEngine::initCopy(Machine *aParent, INetworkAdapter *aAdapter, NATEngine *aThat)
82{
83 AutoInitSpan autoInitSpan(this);
84 AssertReturn(autoInitSpan.isOk(), E_FAIL);
85
86 Log(("initCopy that:%p this:%p\n", aThat, this));
87
88 AutoCaller thatCaller(aThat);
89 AssertComRCReturnRC(thatCaller.rc());
90
91 AutoReadLock thatLock(aThat COMMA_LOCKVAL_SRC_POS);
92
93 mData.attachCopy(aThat->mData);
94 NATRuleMap::iterator it;
95 mNATRules.clear();
96 for (it = aThat->mNATRules.begin(); it != aThat->mNATRules.end(); ++it)
97 {
98 mNATRules.insert(std::make_pair(it->first, it->second));
99 }
100 unconst(mAdapter) = aAdapter;
101 unconst(mParent) = aParent;
102 autoInitSpan.setSucceeded();
103 return BaseFinalConstruct();
104}
105
106
107void NATEngine::FinalRelease()
108{
109 uninit();
110 BaseFinalRelease();
111}
112
113void NATEngine::uninit()
114{
115 AutoUninitSpan autoUninitSpan(this);
116 if (autoUninitSpan.uninitDone())
117 return;
118
119 mNATRules.clear();
120 mData.free();
121 unconst(mPeer) = NULL;
122 unconst(mParent) = NULL;
123}
124
125bool NATEngine::isModified()
126{
127 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
128 bool fModified = m_fModified;
129 return fModified;
130}
131
132bool NATEngine::rollback()
133{
134 AutoCaller autoCaller(this);
135 AssertComRCReturn(autoCaller.rc(), false);
136
137 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
138 bool fChanged = m_fModified;
139
140 if (m_fModified)
141 {
142 /* we need to check all data to see whether anything will be changed
143 * after rollback */
144 mData.rollback();
145 }
146 m_fModified = false;
147 return fChanged;
148}
149
150void NATEngine::commit()
151{
152 AutoCaller autoCaller(this);
153 AssertComRCReturnVoid(autoCaller.rc());
154
155 /* sanity too */
156 AutoCaller peerCaller(mPeer);
157 AssertComRCReturnVoid(peerCaller.rc());
158
159 /* lock both for writing since we modify both (mPeer is "master" so locked
160 * first) */
161 AutoMultiWriteLock2 alock(mPeer, this COMMA_LOCKVAL_SRC_POS);
162 if (m_fModified)
163 {
164 mData.commit();
165 if (mPeer)
166 {
167 mPeer->mData.attach(mData);
168 mPeer->mNATRules.clear();
169 NATRuleMap::iterator it;
170 for (it = mNATRules.begin(); it != mNATRules.end(); ++it)
171 {
172 mPeer->mNATRules.insert(std::make_pair(it->first, it->second));
173 }
174 }
175 }
176 m_fModified = false;
177}
178
179STDMETHODIMP
180NATEngine::GetNetworkSettings(ULONG *aMtu, ULONG *aSockSnd, ULONG *aSockRcv, ULONG *aTcpWndSnd, ULONG *aTcpWndRcv)
181{
182 AutoCaller autoCaller(this);
183 if (FAILED(autoCaller.rc())) return autoCaller.rc();
184
185 AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
186 if (aMtu)
187 *aMtu = mData->mMtu;
188 if (aSockSnd)
189 *aSockSnd = mData->mSockSnd;
190 if (aSockRcv)
191 *aSockRcv = mData->mSockRcv;
192 if (aTcpWndSnd)
193 *aTcpWndSnd = mData->mTcpSnd;
194 if (aTcpWndRcv)
195 *aTcpWndRcv = mData->mTcpRcv;
196
197 return S_OK;
198}
199
200STDMETHODIMP
201NATEngine::SetNetworkSettings(ULONG aMtu, ULONG aSockSnd, ULONG aSockRcv, ULONG aTcpWndSnd, ULONG aTcpWndRcv)
202{
203 AutoCaller autoCaller(this);
204 if (FAILED(autoCaller.rc())) return autoCaller.rc();
205
206 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
207 if ( aMtu || aSockSnd || aSockRcv
208 || aTcpWndSnd || aTcpWndRcv)
209 {
210 mData.backup();
211 m_fModified = true;
212 }
213 if (aMtu)
214 mData->mMtu = aMtu;
215 if (aSockSnd)
216 mData->mSockSnd = aSockSnd;
217 if (aSockRcv)
218 mData->mSockRcv = aSockSnd;
219 if (aTcpWndSnd)
220 mData->mTcpSnd = aTcpWndSnd;
221 if (aTcpWndRcv)
222 mData->mTcpRcv = aTcpWndRcv;
223
224 if (m_fModified)
225 mParent->setModified(Machine::IsModified_NetworkAdapters);
226 return S_OK;
227}
228
229STDMETHODIMP
230NATEngine::COMGETTER(Redirects)(ComSafeArrayOut(BSTR , aNatRules))
231{
232 CheckComArgOutSafeArrayPointerValid(aNatRules);
233
234 AutoCaller autoCaller(this);
235 if (FAILED(autoCaller.rc())) return autoCaller.rc();
236
237 AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
238
239
240 SafeArray<BSTR> sf(mNATRules.size());
241 size_t i = 0;
242 NATRuleMap::const_iterator it;
243 for (it = mNATRules.begin();
244 it != mNATRules.end(); ++it, ++i)
245 {
246 settings::NATRule r = it->second;
247 BstrFmt bstr("%s,%d,%s,%d,%s,%d",
248 r.strName.c_str(),
249 r.proto,
250 r.strHostIP.c_str(),
251 r.u16HostPort,
252 r.strGuestIP.c_str(),
253 r.u16GuestPort);
254 bstr.detachTo(&sf[i]);
255 }
256 sf.detachTo(ComSafeArrayOutArg(aNatRules));
257 return S_OK;
258}
259
260
261STDMETHODIMP
262NATEngine::AddRedirect(IN_BSTR aName, NATProtocol_T aProto, IN_BSTR aBindIp, USHORT aHostPort, IN_BSTR aGuestIP, USHORT aGuestPort)
263{
264
265 AutoCaller autoCaller(this);
266 if (FAILED(autoCaller.rc())) return autoCaller.rc();
267
268 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
269 Utf8Str name = aName;
270 settings::NATRule r;
271 const char *proto;
272 switch (aProto)
273 {
274 case NATProtocol_TCP:
275 proto = "tcp";
276 break;
277 case NATProtocol_UDP:
278 proto = "udp";
279 break;
280 default:
281 return E_INVALIDARG;
282 }
283 if (name.isEmpty())
284 name = Utf8StrFmt("%s_%d_%d", proto, aHostPort, aGuestPort);
285
286 NATRuleMap::iterator it;
287 for (it = mNATRules.begin(); it != mNATRules.end(); ++it)
288 {
289 r = it->second;
290 if (it->first == name)
291 return setError(E_INVALIDARG,
292 tr("A NAT rule of this name already exists"));
293 if ( r.strHostIP == Utf8Str(aBindIp)
294 && r.u16HostPort == aHostPort
295 && r.proto == aProto)
296 return setError(E_INVALIDARG,
297 tr("A NAT rule for this host port and this host IP already exists"));
298 }
299
300 r.strName = name.c_str();
301 r.proto = aProto;
302 r.strHostIP = aBindIp;
303 r.u16HostPort = aHostPort;
304 r.strGuestIP = aGuestIP;
305 r.u16GuestPort = aGuestPort;
306 mNATRules.insert(std::make_pair(name, r));
307 mParent->setModified(Machine::IsModified_NetworkAdapters);
308 m_fModified = true;
309
310 ULONG ulSlot;
311 mAdapter->COMGETTER(Slot)(&ulSlot);
312
313 alock.release();
314 mParent->onNATRedirectRuleChange(ulSlot, FALSE, Bstr(name).raw(), aProto, Bstr(r.strHostIP).raw(), r.u16HostPort, Bstr(r.strGuestIP).raw(), r.u16GuestPort);
315 return S_OK;
316}
317
318STDMETHODIMP
319NATEngine::RemoveRedirect(IN_BSTR aName)
320{
321 AutoCaller autoCaller(this);
322 if (FAILED(autoCaller.rc())) return autoCaller.rc();
323
324 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
325 NATRuleMap::iterator it = mNATRules.find(aName);
326 if (it == mNATRules.end())
327 return E_INVALIDARG;
328 mData.backup();
329 settings::NATRule r = it->second;
330 Utf8Str strHostIP = r.strHostIP;
331 Utf8Str strGuestIP = r.strGuestIP;
332 NATProtocol_T proto = r.proto;
333 uint16_t u16HostPort = r.u16HostPort;
334 uint16_t u16GuestPort = r.u16GuestPort;
335 ULONG ulSlot;
336 mAdapter->COMGETTER(Slot)(&ulSlot);
337
338 mNATRules.erase(it);
339 mParent->setModified(Machine::IsModified_NetworkAdapters);
340 m_fModified = true;
341 alock.release();
342 mParent->onNATRedirectRuleChange(ulSlot, TRUE, aName, proto, Bstr(strHostIP).raw(), u16HostPort, Bstr(strGuestIP).raw(), u16GuestPort);
343 return S_OK;
344}
345
346HRESULT NATEngine::loadSettings(const settings::NAT &data)
347{
348 AutoCaller autoCaller(this);
349 AssertComRCReturnRC(autoCaller.rc());
350
351 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
352 HRESULT rc = S_OK;
353 mData->mNetwork = data.strNetwork;
354 mData->mBindIP = data.strBindIP;
355 mData->mMtu = data.u32Mtu;
356 mData->mSockSnd = data.u32SockSnd;
357 mData->mTcpRcv = data.u32TcpRcv;
358 mData->mTcpSnd = data.u32TcpSnd;
359 /* TFTP */
360 mData->mTFTPPrefix = data.strTFTPPrefix;
361 mData->mTFTPBootFile = data.strTFTPBootFile;
362 mData->mTFTPNextServer = data.strTFTPNextServer;
363 /* DNS */
364 mData->mDNSPassDomain = data.fDNSPassDomain;
365 mData->mDNSProxy = data.fDNSProxy;
366 mData->mDNSUseHostResolver = data.fDNSUseHostResolver;
367 /* Alias */
368 mData->mAliasMode = (data.fAliasUseSamePorts ? NATAliasMode_AliasUseSamePorts : 0);
369 mData->mAliasMode |= (data.fAliasLog ? NATAliasMode_AliasLog : 0);
370 mData->mAliasMode |= (data.fAliasProxyOnly ? NATAliasMode_AliasProxyOnly : 0);
371 /* port forwarding */
372 mNATRules.clear();
373 for (settings::NATRuleList::const_iterator it = data.llRules.begin();
374 it != data.llRules.end(); ++it)
375 {
376 mNATRules.insert(std::make_pair(it->strName, *it));
377 }
378 m_fModified = false;
379 return rc;
380}
381
382
383HRESULT NATEngine::saveSettings(settings::NAT &data)
384{
385 AutoCaller autoCaller(this);
386 AssertComRCReturnRC(autoCaller.rc());
387
388 AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
389 HRESULT rc = S_OK;
390 data.strNetwork = mData->mNetwork;
391 data.strBindIP = mData->mBindIP;
392 data.u32Mtu = mData->mMtu;
393 data.u32SockRcv = mData->mSockRcv;
394 data.u32SockSnd = mData->mSockSnd;
395 data.u32TcpRcv = mData->mTcpRcv;
396 data.u32TcpSnd = mData->mTcpSnd;
397 /* TFTP */
398 data.strTFTPPrefix = mData->mTFTPPrefix;
399 data.strTFTPBootFile = mData->mTFTPBootFile;
400 data.strTFTPNextServer = mData->mTFTPNextServer;
401 /* DNS */
402 data.fDNSPassDomain = !!mData->mDNSPassDomain;
403 data.fDNSProxy = !!mData->mDNSProxy;
404 data.fDNSUseHostResolver = !!mData->mDNSUseHostResolver;
405 /* Alias */
406 data.fAliasLog = !!(mData->mAliasMode & NATAliasMode_AliasLog);
407 data.fAliasProxyOnly = !!(mData->mAliasMode & NATAliasMode_AliasProxyOnly);
408 data.fAliasUseSamePorts = !!(mData->mAliasMode & NATAliasMode_AliasUseSamePorts);
409
410 for (NATRuleMap::iterator it = mNATRules.begin();
411 it != mNATRules.end(); ++it)
412 data.llRules.push_back(it->second);
413 m_fModified = false;
414 return rc;
415}
416
417
418STDMETHODIMP
419NATEngine::COMSETTER(Network)(IN_BSTR aNetwork)
420{
421 AutoCaller autoCaller(this);
422 AssertComRCReturnRC(autoCaller.rc());
423 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
424 if (Bstr(mData->mNetwork) != aNetwork)
425 {
426 mData.backup();
427 mData->mNetwork = aNetwork;
428 mParent->setModified(Machine::IsModified_NetworkAdapters);
429 m_fModified = true;
430 }
431 return S_OK;
432}
433
434STDMETHODIMP
435NATEngine::COMGETTER(Network)(BSTR *aNetwork)
436{
437 CheckComArgNotNull(aNetwork);
438 AutoCaller autoCaller(this);
439 AssertComRCReturnRC(autoCaller.rc());
440
441 AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
442 if (!mData->mNetwork.isEmpty())
443 {
444 mData->mNetwork.cloneTo(aNetwork);
445 Log(("Getter (this:%p) Network: %s\n", this, mData->mNetwork.c_str()));
446 }
447 return S_OK;
448}
449
450STDMETHODIMP
451NATEngine::COMSETTER(HostIP)(IN_BSTR aBindIP)
452{
453 AutoCaller autoCaller(this);
454 AssertComRCReturnRC(autoCaller.rc());
455 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
456 if (Bstr(mData->mBindIP) != aBindIP)
457 {
458 mData.backup();
459 mData->mBindIP = aBindIP;
460 mParent->setModified(Machine::IsModified_NetworkAdapters);
461 m_fModified = true;
462 }
463 return S_OK;
464}
465STDMETHODIMP NATEngine::COMGETTER(HostIP)(BSTR *aBindIP)
466{
467 AutoCaller autoCaller(this);
468 AssertComRCReturnRC(autoCaller.rc());
469
470 AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
471 if (!mData->mBindIP.isEmpty())
472 mData->mBindIP.cloneTo(aBindIP);
473 return S_OK;
474}
475
476
477STDMETHODIMP
478NATEngine::COMSETTER(TFTPPrefix)(IN_BSTR aTFTPPrefix)
479{
480 AutoCaller autoCaller(this);
481 AssertComRCReturnRC(autoCaller.rc());
482 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
483 if (Bstr(mData->mTFTPPrefix) != aTFTPPrefix)
484 {
485 mData.backup();
486 mData->mTFTPPrefix = aTFTPPrefix;
487 mParent->setModified(Machine::IsModified_NetworkAdapters);
488 m_fModified = true;
489 }
490 return S_OK;
491}
492
493STDMETHODIMP
494NATEngine::COMGETTER(TFTPPrefix)(BSTR *aTFTPPrefix)
495{
496 AutoCaller autoCaller(this);
497 AssertComRCReturnRC(autoCaller.rc());
498
499 AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
500 if (!mData->mTFTPPrefix.isEmpty())
501 {
502 mData->mTFTPPrefix.cloneTo(aTFTPPrefix);
503 Log(("Getter (this:%p) TFTPPrefix: %s\n", this, mData->mTFTPPrefix.c_str()));
504 }
505 return S_OK;
506}
507
508STDMETHODIMP
509NATEngine::COMSETTER(TFTPBootFile)(IN_BSTR aTFTPBootFile)
510{
511 AutoCaller autoCaller(this);
512 AssertComRCReturnRC(autoCaller.rc());
513 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
514 if (Bstr(mData->mTFTPBootFile) != aTFTPBootFile)
515 {
516 mData.backup();
517 mData->mTFTPBootFile = aTFTPBootFile;
518 mParent->setModified(Machine::IsModified_NetworkAdapters);
519 m_fModified = true;
520 }
521 return S_OK;
522}
523
524STDMETHODIMP
525NATEngine::COMGETTER(TFTPBootFile)(BSTR *aTFTPBootFile)
526{
527 AutoCaller autoCaller(this);
528 AssertComRCReturnRC(autoCaller.rc());
529
530 AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
531 if (!mData->mTFTPBootFile.isEmpty())
532 {
533 mData->mTFTPBootFile.cloneTo(aTFTPBootFile);
534 Log(("Getter (this:%p) BootFile: %s\n", this, mData->mTFTPBootFile.c_str()));
535 }
536 return S_OK;
537}
538
539STDMETHODIMP
540NATEngine::COMSETTER(TFTPNextServer)(IN_BSTR aTFTPNextServer)
541{
542 AutoCaller autoCaller(this);
543 AssertComRCReturnRC(autoCaller.rc());
544 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
545 if (Bstr(mData->mTFTPNextServer) != aTFTPNextServer)
546 {
547 mData.backup();
548 mData->mTFTPNextServer = aTFTPNextServer;
549 mParent->setModified(Machine::IsModified_NetworkAdapters);
550 m_fModified = true;
551 }
552 return S_OK;
553}
554
555STDMETHODIMP
556NATEngine::COMGETTER(TFTPNextServer)(BSTR *aTFTPNextServer)
557{
558 AutoCaller autoCaller(this);
559 AssertComRCReturnRC(autoCaller.rc());
560
561 AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
562 if (!mData->mTFTPNextServer.isEmpty())
563 {
564 mData->mTFTPNextServer.cloneTo(aTFTPNextServer);
565 Log(("Getter (this:%p) NextServer: %s\n", this, mData->mTFTPNextServer.c_str()));
566 }
567 return S_OK;
568}
569/* DNS */
570STDMETHODIMP
571NATEngine::COMSETTER(DNSPassDomain) (BOOL aDNSPassDomain)
572{
573 AutoCaller autoCaller(this);
574 AssertComRCReturnRC(autoCaller.rc());
575 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
576
577 if (mData->mDNSPassDomain != aDNSPassDomain)
578 {
579 mData.backup();
580 mData->mDNSPassDomain = aDNSPassDomain;
581 mParent->setModified(Machine::IsModified_NetworkAdapters);
582 m_fModified = true;
583 }
584 return S_OK;
585}
586STDMETHODIMP
587NATEngine::COMGETTER(DNSPassDomain)(BOOL *aDNSPassDomain)
588{
589 AutoCaller autoCaller(this);
590 AssertComRCReturnRC(autoCaller.rc());
591
592 AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
593 *aDNSPassDomain = mData->mDNSPassDomain;
594 return S_OK;
595}
596STDMETHODIMP
597NATEngine::COMSETTER(DNSProxy)(BOOL aDNSProxy)
598{
599 AutoCaller autoCaller(this);
600 AssertComRCReturnRC(autoCaller.rc());
601 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
602
603 if (mData->mDNSProxy != aDNSProxy)
604 {
605 mData.backup();
606 mData->mDNSProxy = aDNSProxy;
607 mParent->setModified(Machine::IsModified_NetworkAdapters);
608 m_fModified = true;
609 }
610 return S_OK;
611}
612STDMETHODIMP
613NATEngine::COMGETTER(DNSProxy)(BOOL *aDNSProxy)
614{
615 AutoCaller autoCaller(this);
616 AssertComRCReturnRC(autoCaller.rc());
617
618 AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
619 *aDNSProxy = mData->mDNSProxy;
620 return S_OK;
621}
622STDMETHODIMP
623NATEngine::COMGETTER(DNSUseHostResolver)(BOOL *aDNSUseHostResolver)
624{
625 AutoCaller autoCaller(this);
626 AssertComRCReturnRC(autoCaller.rc());
627 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
628 *aDNSUseHostResolver = mData->mDNSUseHostResolver;
629 return S_OK;
630}
631STDMETHODIMP
632NATEngine::COMSETTER(DNSUseHostResolver)(BOOL aDNSUseHostResolver)
633{
634 AutoCaller autoCaller(this);
635 AssertComRCReturnRC(autoCaller.rc());
636
637 AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
638
639 if (mData->mDNSUseHostResolver != aDNSUseHostResolver)
640 {
641 mData.backup();
642 mData->mDNSUseHostResolver = aDNSUseHostResolver;
643 mParent->setModified(Machine::IsModified_NetworkAdapters);
644 m_fModified = true;
645 }
646 return S_OK;
647}
648
649STDMETHODIMP NATEngine::COMSETTER(AliasMode)(ULONG aAliasMode)
650{
651 AutoCaller autoCaller(this);
652 AssertComRCReturnRC(autoCaller.rc());
653
654 AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
655
656 if (mData->mAliasMode != aAliasMode)
657 {
658 mData.backup();
659 mData->mAliasMode = aAliasMode;
660 mParent->setModified(Machine::IsModified_NetworkAdapters);
661 m_fModified = true;
662 }
663 return S_OK;
664}
665
666STDMETHODIMP NATEngine::COMGETTER(AliasMode)(ULONG *aAliasMode)
667{
668 AutoCaller autoCaller(this);
669 AssertComRCReturnRC(autoCaller.rc());
670 AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
671 *aAliasMode = mData->mAliasMode;
672 return S_OK;
673}
674
Note: See TracBrowser for help on using the repository browser.

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