VirtualBox

source: vbox/trunk/src/VBox/Main/include/GuestCtrlImplPrivate.h@ 47469

Last change on this file since 47469 was 47469, checked in by vboxsync, 11 years ago

Guest Control: Adjustments for supporting < 4.3 Guest Additions in conjunction with the new guest session, extended testcase (now passing using latest 4.2 Guest Additions with latest trunk).

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 13.6 KB
Line 
1/** @file
2 *
3 * Internal helpers/structures for guest control functionality.
4 */
5
6/*
7 * Copyright (C) 2011-2013 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#ifndef ____H_GUESTIMPLPRIVATE
19#define ____H_GUESTIMPLPRIVATE
20
21#include "ConsoleImpl.h"
22
23#include <iprt/asm.h>
24#include <iprt/semaphore.h>
25
26#include <VBox/com/com.h>
27#include <VBox/com/ErrorInfo.h>
28#include <VBox/com/string.h>
29#include <VBox/com/VirtualBox.h>
30
31#include <map>
32#include <vector>
33
34using namespace com;
35
36#ifdef VBOX_WITH_GUEST_CONTROL
37# include <VBox/HostServices/GuestControlSvc.h>
38using namespace guestControl;
39#endif
40
41/** Vector holding a process' CPU affinity. */
42typedef std::vector <LONG> ProcessAffinity;
43/** Vector holding process startup arguments. */
44typedef std::vector <Utf8Str> ProcessArguments;
45
46class GuestProcessStreamBlock;
47class GuestSession;
48
49
50/**
51 * Simple structure mantaining guest credentials.
52 */
53struct GuestCredentials
54{
55 Utf8Str mUser;
56 Utf8Str mPassword;
57 Utf8Str mDomain;
58};
59
60
61typedef std::vector <Utf8Str> GuestEnvironmentArray;
62class GuestEnvironment
63{
64public:
65
66 int BuildEnvironmentBlock(void **ppvEnv, size_t *pcbEnv, uint32_t *pcEnvVars);
67
68 void Clear(void);
69
70 int CopyFrom(const GuestEnvironmentArray &environment);
71
72 int CopyTo(GuestEnvironmentArray &environment);
73
74 static void FreeEnvironmentBlock(void *pvEnv);
75
76 Utf8Str Get(const Utf8Str &strKey);
77
78 Utf8Str Get(size_t nPos);
79
80 bool Has(const Utf8Str &strKey);
81
82 int Set(const Utf8Str &strKey, const Utf8Str &strValue);
83
84 int Set(const Utf8Str &strPair);
85
86 size_t Size(void);
87
88 int Unset(const Utf8Str &strKey);
89
90public:
91
92 GuestEnvironment& operator=(const GuestEnvironmentArray &that);
93
94 GuestEnvironment& operator=(const GuestEnvironment &that);
95
96protected:
97
98 int appendToEnvBlock(const char *pszEnv, void **ppvList, size_t *pcbList, uint32_t *pcEnvVars);
99
100protected:
101
102 std::map <Utf8Str, Utf8Str> mEnvironment;
103};
104
105
106/**
107 * Structure for keeping all the relevant guest file
108 * information around.
109 */
110struct GuestFileOpenInfo
111{
112 /** The filename. */
113 Utf8Str mFileName;
114 /** Then file's opening mode. */
115 Utf8Str mOpenMode;
116 /** The file's disposition mode. */
117 Utf8Str mDisposition;
118 /** Octal creation mode. */
119 uint32_t mCreationMode;
120 /** The initial offset on open. */
121 int64_t mInitialOffset;
122};
123
124
125/**
126 * Structure representing information of a
127 * file system object.
128 */
129struct GuestFsObjData
130{
131 /** Helper function to extract the data from
132 * a certin VBoxService tool's guest stream block. */
133 int FromLs(const GuestProcessStreamBlock &strmBlk);
134 int FromStat(const GuestProcessStreamBlock &strmBlk);
135
136 int64_t mAccessTime;
137 int64_t mAllocatedSize;
138 int64_t mBirthTime;
139 int64_t mChangeTime;
140 uint32_t mDeviceNumber;
141 Utf8Str mFileAttrs;
142 uint32_t mGenerationID;
143 uint32_t mGID;
144 Utf8Str mGroupName;
145 uint32_t mNumHardLinks;
146 int64_t mModificationTime;
147 Utf8Str mName;
148 int64_t mNodeID;
149 uint32_t mNodeIDDevice;
150 int64_t mObjectSize;
151 FsObjType_T mType;
152 uint32_t mUID;
153 uint32_t mUserFlags;
154 Utf8Str mUserName;
155 Utf8Str mACL;
156};
157
158
159/**
160 * Structure for keeping all the relevant guest session
161 * startup parameters around.
162 */
163class GuestSessionStartupInfo
164{
165public:
166
167 GuestSessionStartupInfo(void)
168 : mIsInternal(false /* Non-internal session */),
169 mOpenTimeoutMS(30 * 1000 /* 30s opening timeout */),
170 mOpenFlags(0 /* No opening flags set */) { }
171
172 /** The session's friendly name. Optional. */
173 Utf8Str mName;
174 /** The session's unique ID. Used to encode
175 * a context ID. */
176 uint32_t mID;
177 /** Flag indicating if this is an internal session
178 * or not. Internal session are not accessible by
179 * public API clients. */
180 bool mIsInternal;
181 /** Timeout (in ms) used for opening the session. */
182 uint32_t mOpenTimeoutMS;
183 /** Session opening flags. */
184 uint32_t mOpenFlags;
185};
186
187
188/**
189 * Structure for keeping all the relevant guest process
190 * startup parameters around.
191 */
192class GuestProcessStartupInfo
193{
194public:
195
196 GuestProcessStartupInfo(void)
197 : mFlags(ProcessCreateFlag_None),
198 mTimeoutMS(30 * 1000 /* 30s timeout by default */),
199 mPriority(ProcessPriority_Default) { }
200
201 /** The process' friendly name. */
202 Utf8Str mName;
203 /** The actual command to execute. */
204 Utf8Str mCommand;
205 ProcessArguments mArguments;
206 GuestEnvironment mEnvironment;
207 /** Process creation flags. */
208 uint32_t mFlags;
209 ULONG mTimeoutMS;
210 /** Process priority. */
211 ProcessPriority_T mPriority;
212 /** Process affinity. At the moment we
213 * only support 64 VCPUs. API and
214 * guest can do more already! */
215 uint64_t mAffinity;
216};
217
218
219/**
220 * Class representing the "value" side of a "key=value" pair.
221 */
222class GuestProcessStreamValue
223{
224public:
225
226 GuestProcessStreamValue(void) { }
227 GuestProcessStreamValue(const char *pszValue)
228 : mValue(pszValue) {}
229
230 GuestProcessStreamValue(const GuestProcessStreamValue& aThat)
231 : mValue(aThat.mValue) { }
232
233 Utf8Str mValue;
234};
235
236/** Map containing "key=value" pairs of a guest process stream. */
237typedef std::pair< Utf8Str, GuestProcessStreamValue > GuestCtrlStreamPair;
238typedef std::map < Utf8Str, GuestProcessStreamValue > GuestCtrlStreamPairMap;
239typedef std::map < Utf8Str, GuestProcessStreamValue >::iterator GuestCtrlStreamPairMapIter;
240typedef std::map < Utf8Str, GuestProcessStreamValue >::const_iterator GuestCtrlStreamPairMapIterConst;
241
242/**
243 * Class representing a block of stream pairs (key=value). Each block in a raw guest
244 * output stream is separated by "\0\0", each pair is separated by "\0". The overall
245 * end of a guest stream is marked by "\0\0\0\0".
246 */
247class GuestProcessStreamBlock
248{
249public:
250
251 GuestProcessStreamBlock(void);
252
253 virtual ~GuestProcessStreamBlock(void);
254
255public:
256
257 void Clear(void);
258
259#ifdef DEBUG
260 void DumpToLog(void) const;
261#endif
262
263 int GetInt64Ex(const char *pszKey, int64_t *piVal) const;
264
265 int64_t GetInt64(const char *pszKey) const;
266
267 size_t GetCount(void) const;
268
269 const char* GetString(const char *pszKey) const;
270
271 int GetUInt32Ex(const char *pszKey, uint32_t *puVal) const;
272
273 uint32_t GetUInt32(const char *pszKey) const;
274
275 bool IsEmpty(void) { return mPairs.empty(); }
276
277 int SetValue(const char *pszKey, const char *pszValue);
278
279protected:
280
281 GuestCtrlStreamPairMap mPairs;
282};
283
284/** Vector containing multiple allocated stream pair objects. */
285typedef std::vector< GuestProcessStreamBlock > GuestCtrlStreamObjects;
286typedef std::vector< GuestProcessStreamBlock >::iterator GuestCtrlStreamObjectsIter;
287typedef std::vector< GuestProcessStreamBlock >::const_iterator GuestCtrlStreamObjectsIterConst;
288
289/**
290 * Class for parsing machine-readable guest process output by VBoxService'
291 * toolbox commands ("vbox_ls", "vbox_stat" etc), aka "guest stream".
292 */
293class GuestProcessStream
294{
295
296public:
297
298 GuestProcessStream();
299
300 virtual ~GuestProcessStream();
301
302public:
303
304 int AddData(const BYTE *pbData, size_t cbData);
305
306 void Destroy();
307
308#ifdef DEBUG
309 void Dump(const char *pszFile);
310#endif
311
312 uint32_t GetOffset();
313
314 uint32_t GetSize();
315
316 int ParseBlock(GuestProcessStreamBlock &streamBlock);
317
318protected:
319
320 /** Currently allocated size of internal stream buffer. */
321 uint32_t m_cbAllocated;
322 /** Currently used size of allocated internal stream buffer. */
323 uint32_t m_cbSize;
324 /** Current offset within the internal stream buffer. */
325 uint32_t m_cbOffset;
326 /** Internal stream buffer. */
327 BYTE *m_pbBuffer;
328};
329
330class Guest;
331class Progress;
332
333class GuestTask
334{
335
336public:
337
338 enum TaskType
339 {
340 /** Copies a file from host to the guest. */
341 TaskType_CopyFileToGuest = 50,
342 /** Copies a file from guest to the host. */
343 TaskType_CopyFileFromGuest = 55,
344 /** Update Guest Additions by directly copying the required installer
345 * off the .ISO file, transfer it to the guest and execute the installer
346 * with system privileges. */
347 TaskType_UpdateGuestAdditions = 100
348 };
349
350 GuestTask(TaskType aTaskType, Guest *aThat, Progress *aProgress);
351
352 virtual ~GuestTask();
353
354 int startThread();
355
356 static int taskThread(RTTHREAD aThread, void *pvUser);
357 static int uploadProgress(unsigned uPercent, void *pvUser);
358 static HRESULT setProgressSuccess(ComObjPtr<Progress> pProgress);
359 static HRESULT setProgressErrorMsg(HRESULT hr,
360 ComObjPtr<Progress> pProgress, const char * pszText, ...);
361 static HRESULT setProgressErrorParent(HRESULT hr,
362 ComObjPtr<Progress> pProgress, ComObjPtr<Guest> pGuest);
363
364 TaskType taskType;
365 ComObjPtr<Guest> pGuest;
366 ComObjPtr<Progress> pProgress;
367 HRESULT rc;
368
369 /* Task data. */
370 Utf8Str strSource;
371 Utf8Str strDest;
372 Utf8Str strUserName;
373 Utf8Str strPassword;
374 ULONG uFlags;
375};
376
377class GuestWaitEvent
378{
379
380public:
381
382 GuestWaitEvent(uint32_t mCID, const std::list<VBoxEventType_T> &lstEvents);
383 virtual ~GuestWaitEvent(void);
384
385public:
386
387 uint32_t ContextID(void) { return mCID; };
388 const ComPtr<IEvent> Event(void) { return mEvent; };
389 const std::list<VBoxEventType_T> Types(void) { return mEventTypes; };
390 virtual int Signal(IEvent *pEvent);
391 int Wait(RTMSINTERVAL uTimeoutMS);
392
393protected:
394
395 /* Shutdown indicator. */
396 bool fAborted;
397 /* Associated context ID (CID). */
398 uint32_t mCID;
399 /** List of event types this event should
400 * be signalled on. */
401 std::list<VBoxEventType_T> mEventTypes;
402 /** The event semaphore for triggering
403 * the actual event. */
404 RTSEMEVENT mEventSem;
405 /** Pointer to the actual event. */
406 ComPtr<IEvent> mEvent;
407};
408typedef std::list < GuestWaitEvent* > GuestWaitEvents;
409typedef std::map < VBoxEventType_T, GuestWaitEvents > GuestWaitEventTypes;
410
411class GuestBase
412{
413
414public:
415
416 GuestBase(void);
417 virtual ~GuestBase(void);
418
419public:
420
421 /** For external event listeners. */
422 int signalWaitEvents(VBoxEventType_T aType, IEvent *aEvent);
423
424public:
425
426 int baseInit(void);
427 void baseUninit(void);
428 int cancelWaitEvents(void);
429 int generateContextID(uint32_t uSessionID, uint32_t uObjectID, uint32_t *puContextID);
430 int registerWaitEvent(uint32_t uSessionID, uint32_t uObjectID, const std::list<VBoxEventType_T> &lstEvents, GuestWaitEvent **ppEvent);
431 void unregisterWaitEvent(GuestWaitEvent *pEvent);
432 int waitForEvent(GuestWaitEvent *pEvent, uint32_t uTimeoutMS, VBoxEventType_T *pType, IEvent **ppEvent);
433
434protected:
435
436 /** Pointer to the console object. Needed
437 * for HGCM (VMMDev) communication. */
438 Console *mConsole;
439 /** The next upcoming context ID for this object. */
440 uint32_t mNextContextID;
441 /** Local listener for handling the waiting events
442 * internally. */
443 ComPtr<IEventListener> mLocalListener;
444 /** Critical section for wait events access. */
445 RTCRITSECT mWaitEventCritSect;
446 /** Map of internal events to wait for. */
447 GuestWaitEventTypes mWaitEvents;
448};
449
450/**
451 * Virtual class (interface) for guest objects (processes, files, ...) --
452 * contains all per-object callback management.
453 */
454class GuestObject : public GuestBase
455{
456
457public:
458
459 GuestObject(void);
460 virtual ~GuestObject(void);
461
462public:
463
464 ULONG getObjectID(void) { return mObjectID; }
465
466protected:
467
468 /** Callback dispatcher -- must be implemented by the actual object. */
469 virtual int callbackDispatcher(PVBOXGUESTCTRLHOSTCBCTX pCbCtx, PVBOXGUESTCTRLHOSTCALLBACK pSvcCb) = 0;
470
471protected:
472
473 int bindToSession(Console *pConsole, GuestSession *pSession, uint32_t uObjectID);
474 int registerWaitEvent(const std::list<VBoxEventType_T> &lstEvents, GuestWaitEvent **ppEvent);
475 int sendCommand(uint32_t uFunction, uint32_t uParms, PVBOXHGCMSVCPARM paParms);
476
477protected:
478
479 /**
480 * Commom parameters for all derived objects, when then have
481 * an own mData structure to keep their specific data around.
482 */
483
484 /** Pointer to parent session. Per definition
485 * this objects *always* lives shorter than the
486 * parent. */
487 GuestSession *mSession;
488 /** The object ID -- must be unique for each guest
489 * object and is encoded into the context ID. Must
490 * be set manually when initializing the object.
491 *
492 * For guest processes this is the internal PID,
493 * for guest files this is the internal file ID. */
494 uint32_t mObjectID;
495};
496#endif // ____H_GUESTIMPLPRIVATE
497
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