VirtualBox

source: vbox/trunk/src/VBox/Main/cbinding/tstXPCOMCCall.c@ 18829

Last change on this file since 18829 was 18829, checked in by vboxsync, 16 years ago

undo 45832

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 18.5 KB
Line 
1/* $Revision: 18829 $ */
2/** @file tstXPCOMCGlue.c
3 * Demonstrator program to illustrate use of C bindings of Main API.
4 *
5 * Linux only at the moment due to shared library magic in the Makefile.
6 */
7
8/*
9 * Copyright (C) 2009 Sun Microsystems, Inc.
10 *
11 * This file is part of VirtualBox Open Source Edition (OSE), as
12 * available from http://www.virtualbox.org. This file is free software;
13 * you can redistribute it and/or modify it under the terms of the GNU
14 * General Public License (GPL) as published by the Free Software
15 * Foundation, in version 2 as it comes in the "COPYING" file of the
16 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
17 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
18 *
19 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa
20 * Clara, CA 95054 USA or visit http://www.sun.com if you need
21 * additional information or have any questions.
22 */
23
24/*******************************************************************************
25* Header Files *
26*******************************************************************************/
27#include "VBoxXPCOMCGlue.h"
28#include <stdio.h>
29#include <string.h>
30#include <stdlib.h>
31#include <unistd.h>
32
33static char *nsIDToString(nsID *guid);
34static void listVMs(IVirtualBox *virtualBox, ISession *session);
35
36int volatile g_refcount = 0;
37
38/**
39 * Helper function to convert an nsID into a human readable string.
40 *
41 * @returns result string, allocated. Has to be freed using free()
42 * @param guid Pointer to nsID that will be converted.
43 */
44static char *nsIDToString(nsID *guid)
45{
46 /* Avoid magic number 39. Yes, sizeof "literal" includes the NUL byte. */
47 char *res = malloc(sizeof "{12345678-1234-1234-1234-123456789012}");
48
49 if (res != NULL)
50 {
51 sprintf(res, "{%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x}",
52 (unsigned)guid->m0, (unsigned)guid->m1, (unsigned)guid->m2,
53 (unsigned)guid->m3[0], (unsigned)guid->m3[1],
54 (unsigned)guid->m3[2], (unsigned)guid->m3[3],
55 (unsigned)guid->m3[4], (unsigned)guid->m3[5],
56 (unsigned)guid->m3[6], (unsigned)guid->m3[7]);
57 }
58 return res;
59}
60
61static const char *GetStateName(PRUint32 machineState)
62{
63 switch (machineState)
64 {
65 case MachineState_Null: return "<null>";
66 case MachineState_PoweredOff: return "PoweredOff";
67 case MachineState_Saved: return "Saved";
68 case MachineState_Aborted: return "Aborted";
69 case MachineState_Running: return "Running";
70 case MachineState_Paused: return "Paused";
71 case MachineState_Stuck: return "Stuck";
72 case MachineState_Starting: return "Starting";
73 case MachineState_Stopping: return "Stopping";
74 case MachineState_Saving: return "Saving";
75 case MachineState_Restoring: return "Restoring";
76 case MachineState_Discarding: return "Discarding";
77 case MachineState_SettingUp: return "SettingUp";
78 default: return "no idea";
79 }
80}
81
82static nsresult OnMousePointerShapeChange(
83 IConsoleCallback *pThis,
84 PRBool visible,
85 PRBool alpha,
86 PRUint32 xHot,
87 PRUint32 yHot,
88 PRUint32 width,
89 PRUint32 height,
90 PRUint8 * shape
91) {
92 printf("%d here\n",__LINE__);
93 return 0;
94}
95
96static nsresult OnMouseCapabilityChange(
97 IConsoleCallback *pThis,
98 PRBool supportsAbsolute,
99 PRBool needsHostCursor
100) {
101 printf("%d here\n",__LINE__);
102 return 0;
103}
104
105static nsresult OnKeyboardLedsChange(
106 IConsoleCallback *pThis,
107 PRBool numLock,
108 PRBool capsLock,
109 PRBool scrollLock
110) {
111 printf("%d here\n",__LINE__);
112 return 0;
113}
114
115static nsresult OnStateChange(
116 IConsoleCallback *pThis,
117 PRUint32 state
118) {
119 printf("%d here\n",__LINE__);
120 printf("OnStateChange: %s\n", GetStateName(state));
121 fflush(stdout);
122 return 0;
123}
124
125static nsresult OnAdditionsStateChange(IConsoleCallback *pThis )
126{
127 printf("%d here\n",__LINE__);
128 return 0;
129}
130
131static nsresult OnDVDDriveChange(IConsoleCallback *pThis )
132{
133 printf("%d here\n",__LINE__);
134 return 0;
135}
136
137static nsresult OnFloppyDriveChange(IConsoleCallback *pThis )
138{
139 printf("%d here\n",__LINE__);
140 return 0;
141}
142
143static nsresult OnNetworkAdapterChange(
144 IConsoleCallback *pThis,
145 INetworkAdapter * networkAdapter
146) {
147 printf("%d here\n",__LINE__);
148 return 0;
149}
150
151static nsresult OnSerialPortChange(
152 IConsoleCallback *pThis,
153 ISerialPort * serialPort
154) {
155 printf("%d here\n",__LINE__);
156 return 0;
157}
158
159static nsresult OnParallelPortChange(
160 IConsoleCallback *pThis,
161 IParallelPort * parallelPort
162) {
163 printf("%d here\n",__LINE__);
164 return 0;
165}
166
167static nsresult OnStorageControllerChange(IConsoleCallback *pThis )
168{
169 printf("%d here\n",__LINE__);
170 return 0;
171}
172
173static nsresult OnVRDPServerChange(IConsoleCallback *pThis )
174{
175 printf("%d here\n",__LINE__);
176 return 0;
177}
178
179static nsresult OnUSBControllerChange(IConsoleCallback *pThis )
180{
181 printf("%d here\n",__LINE__);
182 return 0;
183}
184
185static nsresult OnUSBDeviceStateChange(
186 IConsoleCallback *pThis,
187 IUSBDevice * device,
188 PRBool attached,
189 IVirtualBoxErrorInfo * error
190) {
191 printf("%d here\n",__LINE__);
192 return 0;
193}
194
195static nsresult OnSharedFolderChange(
196 IConsoleCallback *pThis,
197 PRUint32 scope
198) {
199 printf("%d here\n",__LINE__);
200 return 0;
201}
202
203static nsresult OnRuntimeError(
204 IConsoleCallback *pThis,
205 PRBool fatal,
206 PRUnichar * id,
207 PRUnichar * message
208) {
209 printf("%d here\n",__LINE__);
210 return 0;
211}
212
213static nsresult OnCanShowWindow(
214 IConsoleCallback *pThis,
215 PRBool * canShow
216) {
217 printf("%d here\n",__LINE__);
218 return 0;
219}
220
221static nsresult OnShowWindow(
222 IConsoleCallback *pThis,
223 PRUint64 * winId
224) {
225 printf("%d here\n",__LINE__);
226 return 0;
227}
228
229
230static nsresult AddRef(nsISupports *pThis)
231{
232 nsresult c;
233
234 printf("AddRef\n");
235 c = g_refcount++;
236 return c;
237}
238
239static nsresult Release(nsISupports *pThis)
240{
241 nsresult c;
242 printf("Release\n");
243
244 c = g_refcount--;
245 if (c == 0)
246 {
247 /* delete object */
248#if 1 /* test */
249 free(pThis->vtbl);
250 free(pThis);
251#endif
252 }
253 return c;
254}
255
256static nsresult QueryInterface(nsISupports *pThis, const nsID *iid, void **resultp)
257{
258 IConsoleCallback *that = (IConsoleCallback *)pThis;
259
260 printf("QueryInterface\n");
261 /* match iid */
262 g_refcount++;
263 *resultp = that;
264 return 0;
265}
266
267static void registerCallBack(IVirtualBox *virtualBox, ISession *session, nsID *machineId)
268{
269 IConsole *console = NULL;
270 nsresult rc;
271
272 rc = virtualBox->vtbl->OpenExistingSession(virtualBox, session, machineId);
273 session->vtbl->GetConsole(session, &console);
274 if (console) {
275 IConsoleCallback *consoleCallback = NULL;
276
277 consoleCallback = calloc(1, sizeof(IConsoleCallback));
278 consoleCallback->vtbl = calloc(1, sizeof(struct IConsoleCallback_vtbl));
279
280 if (consoleCallback && consoleCallback->vtbl) {
281
282 consoleCallback->vtbl->nsisupports.AddRef = &AddRef;
283 consoleCallback->vtbl->nsisupports.Release = &Release;
284 consoleCallback->vtbl->nsisupports.QueryInterface = &QueryInterface;
285 consoleCallback->vtbl->OnMousePointerShapeChange = &OnMousePointerShapeChange;
286 consoleCallback->vtbl->OnMouseCapabilityChange = &OnMouseCapabilityChange;
287 consoleCallback->vtbl->OnKeyboardLedsChange =&OnKeyboardLedsChange;
288 consoleCallback->vtbl->OnStateChange = &OnStateChange;
289 consoleCallback->vtbl->OnAdditionsStateChange = &OnAdditionsStateChange;
290 consoleCallback->vtbl->OnDVDDriveChange = &OnDVDDriveChange;
291 consoleCallback->vtbl->OnFloppyDriveChange = &OnFloppyDriveChange;
292 consoleCallback->vtbl->OnNetworkAdapterChange = &OnNetworkAdapterChange;
293 consoleCallback->vtbl->OnSerialPortChange = &OnSerialPortChange;
294 consoleCallback->vtbl->OnParallelPortChange = &OnParallelPortChange;
295 consoleCallback->vtbl->OnStorageControllerChange = &OnStorageControllerChange;
296 consoleCallback->vtbl->OnVRDPServerChange = &OnVRDPServerChange;
297 consoleCallback->vtbl->OnUSBControllerChange = &OnUSBControllerChange;
298 consoleCallback->vtbl->OnUSBDeviceStateChange = &OnUSBDeviceStateChange;
299 consoleCallback->vtbl->OnSharedFolderChange = &OnSharedFolderChange;
300 consoleCallback->vtbl->OnRuntimeError = &OnRuntimeError;
301 consoleCallback->vtbl->OnCanShowWindow = &OnCanShowWindow;
302 consoleCallback->vtbl->OnShowWindow = &OnShowWindow;
303 g_refcount = 1;
304
305 printf("%d here\n",__LINE__);
306 console->vtbl->RegisterCallback(console, consoleCallback);
307 printf("%d here\n",__LINE__);
308
309 {
310 int run = 10;
311 while (run-- > 0) {
312 sleep(1);
313 printf("waiting here:%d\n",run);
314 fflush(stdout);
315 }
316 }
317 console->vtbl->UnregisterCallback(console, consoleCallback);
318 }
319 /*consoleCallback->vtbl->Release(consoleCallback);*/
320 }
321 session->vtbl->Close((void *)session);
322}
323
324/**
325 * List the registered VMs.
326 *
327 * @param virtualBox ptr to IVirtualBox object
328 * @param session ptr to ISession object
329 */
330static void listVMs(IVirtualBox *virtualBox, ISession *session)
331{
332 nsresult rc;
333 IMachine **machines = NULL;
334 PRUint32 machineCnt = 0;
335 PRUint32 i;
336 unsigned start_id;
337
338 /*
339 * Get the list of all registered VMs.
340 */
341
342 rc = virtualBox->vtbl->GetMachines(virtualBox, &machineCnt, &machines);
343 if (NS_FAILED(rc))
344 {
345 fprintf(stderr, "could not get list of machines, rc=%08x\n",
346 (unsigned)rc);
347 return;
348 }
349
350 if (machineCnt == 0)
351 {
352 printf("\tNo VMs\n");
353 return;
354 }
355
356 printf("VM List:\n\n");
357
358 /*
359 * Iterate through the collection.
360 */
361
362 for (i = 0; i < machineCnt; ++i)
363 {
364 IMachine *machine = machines[i];
365 PRBool isAccessible = PR_FALSE;
366
367 printf("\tMachine #%u\n", (unsigned)i);
368
369 if (!machine)
370 {
371 printf("\t(skipped, NULL)\n");
372 continue;
373 }
374
375 machine->vtbl->GetAccessible(machine, &isAccessible);
376
377 if (isAccessible)
378 {
379 PRUnichar *machineNameUtf16;
380 char *machineName;
381
382 machine->vtbl->GetName(machine, &machineNameUtf16);
383 g_pVBoxFuncs->pfnUtf16ToUtf8(machineNameUtf16,&machineName);
384 printf("\tName: %s\n", machineName);
385
386 g_pVBoxFuncs->pfnUtf8Free(machineName);
387 g_pVBoxFuncs->pfnComUnallocMem(machineNameUtf16);
388 }
389 else
390 {
391 printf("\tName: <inaccessible>\n");
392 }
393
394
395 {
396 nsID *iid = NULL;
397 char *uuidString;
398
399 machine->vtbl->GetId(machine, &iid);
400 uuidString = nsIDToString(iid);
401 printf("\tUUID: %s\n", uuidString);
402
403 free(uuidString);
404 g_pVBoxFuncs->pfnComUnallocMem(iid);
405 }
406
407 if (isAccessible)
408 {
409 {
410 PRUnichar *configFile;
411 char *configFile1 = calloc((size_t)64, (size_t)1);
412
413 machine->vtbl->GetSettingsFilePath(machine, &configFile);
414 g_pVBoxFuncs->pfnUtf16ToUtf8(configFile, &configFile1);
415 printf("\tConfig file: %s\n", configFile1);
416
417 free(configFile1);
418 g_pVBoxFuncs->pfnComUnallocMem(configFile);
419 }
420
421 {
422 PRUint32 memorySize;
423
424 machine->vtbl->GetMemorySize(machine, &memorySize);
425 printf("\tMemory size: %uMB\n", memorySize);
426 }
427
428 {
429 PRUnichar *typeId;
430 PRUnichar *osNameUtf16;
431 char *osName;
432 IGuestOSType *osType = NULL;
433
434 machine->vtbl->GetOSTypeId(machine, &typeId);
435 virtualBox->vtbl->GetGuestOSType(virtualBox, typeId, &osType);
436 osType->vtbl->GetDescription(osType, &osNameUtf16);
437 g_pVBoxFuncs->pfnUtf16ToUtf8(osNameUtf16,&osName);
438 printf("\tGuest OS: %s\n\n", osName);
439
440 osType->vtbl->nsisupports.Release((void *)osType);
441 g_pVBoxFuncs->pfnUtf8Free(osName);
442 g_pVBoxFuncs->pfnComUnallocMem(osNameUtf16);
443 g_pVBoxFuncs->pfnComUnallocMem(typeId);
444 }
445 }
446 }
447
448 /*
449 * Let the user chose a machine to start.
450 */
451
452 printf("Type Machine# to start (0 - %u) or 'quit' to do nothing: ",
453 (unsigned)(machineCnt - 1));
454 fflush(stdout);
455
456 if (scanf("%u", &start_id) == 1 && start_id < machineCnt)
457 {
458 IMachine *machine = machines[start_id];
459
460 if (machine)
461 {
462 nsID *iid = NULL;
463
464 machine->vtbl->GetId(machine, &iid);
465 /*startVM(virtualBox, session, iid);*/
466 registerCallBack(virtualBox, session, iid);
467
468 g_pVBoxFuncs->pfnComUnallocMem(iid);
469 }
470 }
471
472 /*
473 * Don't forget to release the objects in the array.
474 */
475
476 for (i = 0; i < machineCnt; ++i)
477 {
478 IMachine *machine = machines[i];
479
480 if (machine)
481 {
482 machine->vtbl->nsisupports.Release((nsISupports *)machine);
483 }
484 }
485}
486
487/**
488 * Start a VM.
489 *
490 * @param virtualBox ptr to IVirtualBox object
491 * @param session ptr to ISession object
492 * @param id identifies the machine to start
493 */
494#if 0
495static void startVM(IVirtualBox *virtualBox, ISession *session, nsID *id)
496{
497 nsresult rc;
498 IMachine *machine = NULL;
499 IProgress *progress = NULL;
500 PRUnichar *env = NULL;
501 PRUnichar *sessionType;
502
503 rc = virtualBox->vtbl->GetMachine(virtualBox, id, &machine);
504
505 if (NS_FAILED(rc) || !machine)
506 {
507 fprintf(stderr, "Error: Couldn't get the machine handle.\n");
508 return;
509 }
510
511 g_pVBoxFuncs->pfnUtf8ToUtf16("gui", &sessionType);
512
513 rc = virtualBox->vtbl->OpenRemoteSession(
514 virtualBox,
515 session,
516 id,
517 sessionType,
518 env,
519 &progress
520 );
521
522 g_pVBoxFuncs->pfnUtf16Free(sessionType);
523
524 if (NS_FAILED(rc))
525 {
526 fprintf(stderr, "Error: OpenRemoteSession failed.\n");
527 }
528 else
529 {
530 PRBool completed;
531 nsresult resultCode;
532
533 printf("Waiting for the remote session to open...\n");
534 progress->vtbl->WaitForCompletion(progress, -1);
535
536 rc = progress->vtbl->GetCompleted(progress, &completed);
537 if (NS_FAILED(rc))
538 {
539 fprintf (stderr, "Error: GetCompleted status failed.\n");
540 }
541
542 progress->vtbl->GetResultCode(progress, &resultCode);
543 if (NS_FAILED(resultCode))
544 {
545 IVirtualBoxErrorInfo *errorInfo;
546 PRUnichar *textUtf16;
547 char *text;
548
549 progress->vtbl->GetErrorInfo(progress, &errorInfo);
550 errorInfo->vtbl->GetText(errorInfo, &textUtf16);
551 g_pVBoxFuncs->pfnUtf16ToUtf8(textUtf16, &text);
552 printf("Error: %s\n", text);
553
554 g_pVBoxFuncs->pfnComUnallocMem(textUtf16);
555 g_pVBoxFuncs->pfnUtf8Free(text);
556 }
557 else
558 {
559 fprintf(stderr, "Remote session has been successfully opened.\n");
560 }
561 progress->vtbl->nsisupports.Release((void *)progress);
562 }
563
564 /* It's important to always release resources. */
565 machine->vtbl->nsisupports.Release((void *)machine);
566}
567#endif
568
569/* Main - Start the ball rolling. */
570
571int main(int argc, char **argv)
572{
573 IVirtualBox *vbox = NULL;
574 ISession *session = NULL;
575 PRUint32 revision = 0;
576 PRUnichar *versionUtf16 = NULL;
577 PRUnichar *homefolderUtf16 = NULL;
578 nsresult rc; /* Result code of various function (method) calls. */
579
580 printf("Starting Main\n");
581
582 /*
583 * VBoxComInitialize does all the necessary startup action and
584 * provides us with pointers to vbox and session handles.
585 * It should be matched by a call to VBoxComUninitialize(vbox)
586 * when done.
587 */
588
589 if (VBoxCGlueInit() != 0)
590 {
591 fprintf(stderr, "%s: FATAL: VBoxCGlueInit failed: %s\n",
592 argv[0], g_szVBoxErrMsg);
593 return EXIT_FAILURE;
594 }
595
596 g_pVBoxFuncs->pfnComInitialize(&vbox, &session);
597 if (vbox == NULL)
598 {
599 fprintf(stderr, "%s: FATAL: could not get vbox handle\n", argv[0]);
600 return EXIT_FAILURE;
601 }
602 if (session == NULL)
603 {
604 fprintf(stderr, "%s: FATAL: could not get session handle\n", argv[0]);
605 return EXIT_FAILURE;
606 }
607
608 /*
609 * Now ask for revision, version and home folder information of
610 * this vbox. Were not using fancy macros here so it
611 * remains easy to see how we access C++'s vtable.
612 */
613
614 printf("----------------------------------------------------\n");
615
616 /* 1. Revision */
617
618 rc = vbox->vtbl->GetRevision(vbox, &revision);
619 if (NS_SUCCEEDED(rc))
620 {
621 printf("\tRevision: %u\n", revision);
622 }
623 else
624 {
625 fprintf(stderr, "%s: GetRevision() returned %08x\n",
626 argv[0], (unsigned)rc);
627 }
628
629 /* 2. Version */
630
631 rc = vbox->vtbl->GetVersion(vbox, &versionUtf16);
632 if (NS_SUCCEEDED(rc))
633 {
634 char *version = NULL;
635 g_pVBoxFuncs->pfnUtf16ToUtf8(versionUtf16, &version);
636 printf("\tVersion: %s\n", version);
637 g_pVBoxFuncs->pfnUtf8Free(version);
638 g_pVBoxFuncs->pfnComUnallocMem(versionUtf16);
639 }
640 else
641 {
642 fprintf(stderr, "%s: GetVersion() returned %08x\n",
643 argv[0], (unsigned)rc);
644 }
645
646 /* 3. Home Folder */
647
648 rc = vbox->vtbl->GetHomeFolder(vbox, &homefolderUtf16);
649 if (NS_SUCCEEDED(rc))
650 {
651 char *homefolder = NULL;
652 g_pVBoxFuncs->pfnUtf16ToUtf8(homefolderUtf16, &homefolder);
653 printf("\tHomeFolder: %s\n", homefolder);
654 g_pVBoxFuncs->pfnUtf8Free(homefolder);
655 g_pVBoxFuncs->pfnComUnallocMem(homefolderUtf16);
656 }
657 else
658 {
659 fprintf(stderr, "%s: GetHomeFolder() returned %08x\n",
660 argv[0], (unsigned)rc);
661 }
662
663 listVMs(vbox, session);
664 session->vtbl->Close(session);
665
666 printf("----------------------------------------------------\n");
667
668 /*
669 * Do as mom told us: always clean up after yourself.
670 */
671
672 g_pVBoxFuncs->pfnComUninitialize();
673 VBoxCGlueTerm();
674 printf("Finished Main\n");
675
676 return 0;
677}
678/* vim: set ts=4 sw=4 et: */
Note: See TracBrowser for help on using the repository browser.

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