[43363] | 1 | /* $Id: VBoxGuest-haiku.c 100267 2023-06-23 14:57:53Z vboxsync $ */
|
---|
| 2 | /** @file
|
---|
| 3 | * VBoxGuest kernel module, Haiku Guest Additions, implementation.
|
---|
| 4 | */
|
---|
| 5 |
|
---|
| 6 | /*
|
---|
[98103] | 7 | * Copyright (C) 2012-2023 Oracle and/or its affiliates.
|
---|
[43363] | 8 | *
|
---|
[96407] | 9 | * This file is part of VirtualBox base platform packages, as
|
---|
| 10 | * available from https://www.virtualbox.org.
|
---|
[69308] | 11 | *
|
---|
[96407] | 12 | * This program is free software; you can redistribute it and/or
|
---|
| 13 | * modify it under the terms of the GNU General Public License
|
---|
| 14 | * as published by the Free Software Foundation, in version 3 of the
|
---|
| 15 | * License.
|
---|
| 16 | *
|
---|
| 17 | * This program is distributed in the hope that it will be useful, but
|
---|
| 18 | * WITHOUT ANY WARRANTY; without even the implied warranty of
|
---|
| 19 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
---|
| 20 | * General Public License for more details.
|
---|
| 21 | *
|
---|
| 22 | * You should have received a copy of the GNU General Public License
|
---|
| 23 | * along with this program; if not, see <https://www.gnu.org/licenses>.
|
---|
| 24 | *
|
---|
[69308] | 25 | * The contents of this file may alternatively be used under the terms
|
---|
| 26 | * of the Common Development and Distribution License Version 1.0
|
---|
[96407] | 27 | * (CDDL), a copy of it is provided in the "COPYING.CDDL" file included
|
---|
| 28 | * in the VirtualBox distribution, in which case the provisions of the
|
---|
[69308] | 29 | * CDDL are applicable instead of those of the GPL.
|
---|
| 30 | *
|
---|
| 31 | * You may elect to license modified versions of this file under the
|
---|
| 32 | * terms and conditions of either the GPL or the CDDL or both.
|
---|
[96407] | 33 | *
|
---|
| 34 | * SPDX-License-Identifier: GPL-3.0-only OR CDDL-1.0
|
---|
[43363] | 35 | */
|
---|
| 36 |
|
---|
| 37 | /*
|
---|
| 38 | * This code is based on:
|
---|
| 39 | *
|
---|
| 40 | * VirtualBox Guest Additions for Haiku.
|
---|
| 41 | * Copyright (c) 2011 Mike Smith <mike@scgtrp.net>
|
---|
[54608] | 42 | * François Revol <revol@free.fr>
|
---|
[43363] | 43 | *
|
---|
| 44 | * Permission is hereby granted, free of charge, to any person
|
---|
| 45 | * obtaining a copy of this software and associated documentation
|
---|
| 46 | * files (the "Software"), to deal in the Software without
|
---|
| 47 | * restriction, including without limitation the rights to use,
|
---|
| 48 | * copy, modify, merge, publish, distribute, sublicense, and/or sell
|
---|
| 49 | * copies of the Software, and to permit persons to whom the
|
---|
| 50 | * Software is furnished to do so, subject to the following
|
---|
| 51 | * conditions:
|
---|
| 52 | *
|
---|
| 53 | * The above copyright notice and this permission notice shall be
|
---|
| 54 | * included in all copies or substantial portions of the Software.
|
---|
| 55 | *
|
---|
| 56 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
---|
| 57 | * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
---|
| 58 | * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
---|
| 59 | * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
---|
| 60 | * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
---|
| 61 | * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
---|
| 62 | * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
---|
| 63 | * OTHER DEALINGS IN THE SOFTWARE.
|
---|
| 64 | */
|
---|
| 65 |
|
---|
[57358] | 66 |
|
---|
| 67 | /*********************************************************************************************************************************
|
---|
| 68 | * Header Files *
|
---|
| 69 | *********************************************************************************************************************************/
|
---|
[43363] | 70 | #define IN_VBOXGUEST
|
---|
| 71 | #include <sys/param.h>
|
---|
| 72 | #include <sys/types.h>
|
---|
| 73 | #include <sys/uio.h>
|
---|
| 74 | #include <OS.h>
|
---|
| 75 | #include <Drivers.h>
|
---|
| 76 | #include <KernelExport.h>
|
---|
| 77 | #include <PCI.h>
|
---|
| 78 |
|
---|
| 79 | #include "VBoxGuest-haiku.h"
|
---|
| 80 | #include "VBoxGuestInternal.h"
|
---|
| 81 | #include <VBox/log.h>
|
---|
| 82 | #include <iprt/assert.h>
|
---|
| 83 | #include <iprt/initterm.h>
|
---|
| 84 | #include <iprt/process.h>
|
---|
| 85 | #include <iprt/mem.h>
|
---|
| 86 | #include <iprt/memobj.h>
|
---|
| 87 | #include <iprt/asm.h>
|
---|
| 88 | #include <iprt/timer.h>
|
---|
| 89 | #include <iprt/heap.h>
|
---|
| 90 |
|
---|
[58113] | 91 |
|
---|
| 92 | /*********************************************************************************************************************************
|
---|
| 93 | * Defined Constants And Macros *
|
---|
| 94 | *********************************************************************************************************************************/
|
---|
[43363] | 95 | #define MODULE_NAME VBOXGUEST_MODULE_NAME
|
---|
| 96 |
|
---|
[58113] | 97 |
|
---|
| 98 | /*********************************************************************************************************************************
|
---|
| 99 | * Internal Functions *
|
---|
| 100 | *********************************************************************************************************************************/
|
---|
[43363] | 101 | /*
|
---|
| 102 | * IRQ related functions.
|
---|
| 103 | */
|
---|
[58113] | 104 | static void vgdrvHaikuRemoveIRQ(void *pvState);
|
---|
| 105 | static int vgdrvHaikuAddIRQ(void *pvState);
|
---|
| 106 | static int32 vgdrvHaikuISR(void *pvState);
|
---|
[43363] | 107 |
|
---|
| 108 |
|
---|
[58113] | 109 | /*********************************************************************************************************************************
|
---|
| 110 | * Global Variables *
|
---|
| 111 | *********************************************************************************************************************************/
|
---|
[43363] | 112 | static status_t std_ops(int32 op, ...);
|
---|
| 113 |
|
---|
| 114 | static RTSPINLOCK g_Spinlock = NIL_RTSPINLOCK;
|
---|
| 115 |
|
---|
| 116 | int32 api_version = B_CUR_DRIVER_API_VERSION;
|
---|
| 117 |
|
---|
| 118 | /** List of cloned device. Managed by the kernel. */
|
---|
[58113] | 119 | //static struct clonedevs *g_pvgdrvHaikuClones;
|
---|
[43363] | 120 | /** The dev_clone event handler tag. */
|
---|
[58113] | 121 | //static eventhandler_tag g_vgdrvHaikuEHTag;
|
---|
[43363] | 122 | /** selinfo structure used for polling. */
|
---|
| 123 | //static struct selinfo g_SelInfo;
|
---|
| 124 | /** PCI Bus Manager Module */
|
---|
| 125 | static pci_module_info *gPCI;
|
---|
| 126 |
|
---|
[43366] | 127 | static struct vboxguest_module_info g_VBoxGuest =
|
---|
| 128 | {
|
---|
[43363] | 129 | {
|
---|
| 130 | MODULE_NAME,
|
---|
| 131 | 0,
|
---|
| 132 | std_ops
|
---|
| 133 | },
|
---|
[43366] | 134 | { 0 },
|
---|
| 135 | { 0 },
|
---|
[43363] | 136 | 0,
|
---|
| 137 | RTLogBackdoorPrintf,
|
---|
| 138 | RTLogBackdoorPrintfV,
|
---|
| 139 | RTLogSetDefaultInstanceThread,
|
---|
| 140 | RTMemAllocExTag,
|
---|
| 141 | RTMemContAlloc,
|
---|
| 142 | RTMemContFree,
|
---|
| 143 | RTMemFreeEx,
|
---|
| 144 | RTMpIsCpuPossible,
|
---|
| 145 | RTMpNotificationDeregister,
|
---|
| 146 | RTMpNotificationRegister,
|
---|
| 147 | RTMpOnAll,
|
---|
| 148 | RTMpOnOthers,
|
---|
| 149 | RTMpOnSpecific,
|
---|
| 150 | RTPowerNotificationDeregister,
|
---|
| 151 | RTPowerNotificationRegister,
|
---|
| 152 | RTPowerSignalEvent,
|
---|
| 153 | RTR0AssertPanicSystem,
|
---|
| 154 | RTR0Init,
|
---|
| 155 | RTR0MemObjAddress,
|
---|
| 156 | RTR0MemObjAddressR3,
|
---|
| 157 | RTR0MemObjAllocContTag,
|
---|
| 158 | RTR0MemObjAllocLowTag,
|
---|
| 159 | RTR0MemObjAllocPageTag,
|
---|
| 160 | RTR0MemObjAllocPhysExTag,
|
---|
| 161 | RTR0MemObjAllocPhysNCTag,
|
---|
| 162 | RTR0MemObjAllocPhysTag,
|
---|
| 163 | RTR0MemObjEnterPhysTag,
|
---|
| 164 | RTR0MemObjFree,
|
---|
| 165 | RTR0MemObjGetPagePhysAddr,
|
---|
| 166 | RTR0MemObjIsMapping,
|
---|
| 167 | RTR0MemObjLockKernelTag,
|
---|
| 168 | RTR0MemObjLockUserTag,
|
---|
| 169 | RTR0MemObjMapKernelExTag,
|
---|
| 170 | RTR0MemObjMapKernelTag,
|
---|
| 171 | RTR0MemObjMapUserTag,
|
---|
| 172 | RTR0MemObjProtect,
|
---|
| 173 | RTR0MemObjReserveKernelTag,
|
---|
| 174 | RTR0MemObjReserveUserTag,
|
---|
| 175 | RTR0MemObjSize,
|
---|
| 176 | RTR0ProcHandleSelf,
|
---|
| 177 | RTR0Term,
|
---|
| 178 | RTR0TermForced,
|
---|
| 179 | RTProcSelf,
|
---|
| 180 | RTSemEventGetResolution,
|
---|
| 181 | RTSemEventMultiGetResolution,
|
---|
| 182 | RTSemEventMultiWaitEx,
|
---|
| 183 | RTSemEventMultiWaitExDebug,
|
---|
| 184 | RTSemEventWaitEx,
|
---|
| 185 | RTSemEventWaitExDebug,
|
---|
| 186 | RTThreadIsInInterrupt,
|
---|
| 187 | RTThreadPreemptDisable,
|
---|
| 188 | RTThreadPreemptIsEnabled,
|
---|
| 189 | RTThreadPreemptIsPending,
|
---|
| 190 | RTThreadPreemptIsPendingTrusty,
|
---|
| 191 | RTThreadPreemptIsPossible,
|
---|
| 192 | RTThreadPreemptRestore,
|
---|
| 193 | RTTimerGetSystemGranularity,
|
---|
| 194 | RTTimerReleaseSystemGranularity,
|
---|
| 195 | RTTimerRequestSystemGranularity,
|
---|
| 196 | RTSpinlockAcquire,
|
---|
| 197 | RTSpinlockRelease,
|
---|
| 198 | RTMemTmpAllocTag,
|
---|
| 199 | RTMemTmpFree,
|
---|
| 200 | RTLogDefaultInstance,
|
---|
[55980] | 201 | RTLogDefaultInstanceEx,
|
---|
| 202 | RTLogRelGetDefaultInstance,
|
---|
| 203 | RTLogRelGetDefaultInstanceEx,
|
---|
[43363] | 204 | RTErrConvertToErrno,
|
---|
[58053] | 205 | VGDrvCommonIoCtl,
|
---|
| 206 | VGDrvCommonCreateUserSession,
|
---|
| 207 | VGDrvCommonCloseSession,
|
---|
[43363] | 208 | VBoxGuestIDCOpen,
|
---|
| 209 | VBoxGuestIDCClose,
|
---|
| 210 | VBoxGuestIDCCall,
|
---|
| 211 | RTAssertMsg1Weak,
|
---|
| 212 | RTAssertMsg2Weak,
|
---|
| 213 | RTAssertMsg2WeakV,
|
---|
| 214 | RTAssertShouldPanic,
|
---|
| 215 | RTSemFastMutexCreate,
|
---|
| 216 | RTSemFastMutexDestroy,
|
---|
| 217 | RTSemFastMutexRelease,
|
---|
| 218 | RTSemFastMutexRequest,
|
---|
| 219 | RTSemMutexCreate,
|
---|
| 220 | RTSemMutexDestroy,
|
---|
| 221 | RTSemMutexRelease,
|
---|
| 222 | RTSemMutexRequest,
|
---|
| 223 | RTHeapSimpleRelocate,
|
---|
| 224 | RTHeapOffsetInit,
|
---|
| 225 | RTHeapSimpleInit,
|
---|
| 226 | RTHeapOffsetAlloc,
|
---|
| 227 | RTHeapSimpleAlloc,
|
---|
| 228 | RTHeapOffsetFree,
|
---|
| 229 | RTHeapSimpleFree
|
---|
| 230 | };
|
---|
| 231 |
|
---|
| 232 | #if 0
|
---|
| 233 | /**
|
---|
| 234 | * DEVFS event handler.
|
---|
| 235 | */
|
---|
[58113] | 236 | static void vgdrvHaikuClone(void *pvArg, struct ucred *pCred, char *pszName, int cchName, struct cdev **ppDev)
|
---|
[43363] | 237 | {
|
---|
| 238 | int iUnit;
|
---|
| 239 | int rc;
|
---|
| 240 |
|
---|
[58113] | 241 | Log(("vgdrvHaikuClone: pszName=%s ppDev=%p\n", pszName, ppDev));
|
---|
[43363] | 242 |
|
---|
| 243 | /*
|
---|
| 244 | * One device node per user, si_drv1 points to the session.
|
---|
| 245 | * /dev/vboxguest<N> where N = {0...255}.
|
---|
| 246 | */
|
---|
| 247 | if (!ppDev)
|
---|
[43366] | 248 | return;
|
---|
[43363] | 249 | if (strcmp(pszName, "vboxguest") == 0)
|
---|
[43366] | 250 | iUnit = -1;
|
---|
[43363] | 251 | else if (dev_stdclone(pszName, NULL, "vboxguest", &iUnit) != 1)
|
---|
[43366] | 252 | return;
|
---|
[43363] | 253 | if (iUnit >= 256)
|
---|
| 254 | {
|
---|
[58113] | 255 | Log(("vgdrvHaikuClone: iUnit=%d >= 256 - rejected\n", iUnit));
|
---|
[43363] | 256 | return;
|
---|
| 257 | }
|
---|
| 258 |
|
---|
[58113] | 259 | Log(("vgdrvHaikuClone: pszName=%s iUnit=%d\n", pszName, iUnit));
|
---|
[43363] | 260 |
|
---|
[58113] | 261 | rc = clone_create(&g_pvgdrvHaikuClones, &g_vgdrvHaikuDeviceHooks, &iUnit, ppDev, 0);
|
---|
| 262 | Log(("vgdrvHaikuClone: clone_create -> %d; iUnit=%d\n", rc, iUnit));
|
---|
[43363] | 263 | if (rc)
|
---|
| 264 | {
|
---|
[58113] | 265 | *ppDev = make_dev(&g_vgdrvHaikuDeviceHooks,
|
---|
[43363] | 266 | iUnit,
|
---|
| 267 | UID_ROOT,
|
---|
| 268 | GID_WHEEL,
|
---|
| 269 | 0644,
|
---|
| 270 | "vboxguest%d", iUnit);
|
---|
| 271 | if (*ppDev)
|
---|
| 272 | {
|
---|
| 273 | dev_ref(*ppDev);
|
---|
| 274 | (*ppDev)->si_flags |= SI_CHEAPCLONE;
|
---|
[58113] | 275 | Log(("vgdrvHaikuClone: Created *ppDev=%p iUnit=%d si_drv1=%p si_drv2=%p\n",
|
---|
[43366] | 276 | *ppDev, iUnit, (*ppDev)->si_drv1, (*ppDev)->si_drv2));
|
---|
[43363] | 277 | (*ppDev)->si_drv1 = (*ppDev)->si_drv2 = NULL;
|
---|
| 278 | }
|
---|
| 279 | else
|
---|
[58113] | 280 | Log(("vgdrvHaikuClone: make_dev iUnit=%d failed\n", iUnit));
|
---|
[43363] | 281 | }
|
---|
| 282 | else
|
---|
[58113] | 283 | Log(("vgdrvHaikuClone: Existing *ppDev=%p iUnit=%d si_drv1=%p si_drv2=%p\n",
|
---|
[43366] | 284 | *ppDev, iUnit, (*ppDev)->si_drv1, (*ppDev)->si_drv2));
|
---|
[43363] | 285 | }
|
---|
| 286 | #endif
|
---|
| 287 |
|
---|
[43410] | 288 |
|
---|
[58113] | 289 | static status_t vgdrvHaikuDetach(void)
|
---|
[43363] | 290 | {
|
---|
| 291 | struct VBoxGuestDeviceState *pState = &sState;
|
---|
| 292 |
|
---|
| 293 | if (cUsers > 0)
|
---|
| 294 | return EBUSY;
|
---|
| 295 |
|
---|
| 296 | /*
|
---|
[58113] | 297 | * Reverse what we did in vgdrvHaikuAttach.
|
---|
[43363] | 298 | */
|
---|
[58113] | 299 | vgdrvHaikuRemoveIRQ(pState);
|
---|
[43363] | 300 |
|
---|
| 301 | if (pState->iVMMDevMemAreaId)
|
---|
| 302 | delete_area(pState->iVMMDevMemAreaId);
|
---|
| 303 |
|
---|
[58053] | 304 | VGDrvCommonDeleteDevExt(&g_DevExt);
|
---|
[43363] | 305 |
|
---|
| 306 | #ifdef DO_LOG
|
---|
| 307 | RTLogDestroy(RTLogRelSetDefaultInstance(NULL));
|
---|
| 308 | RTLogSetDefaultInstance(NULL);
|
---|
| 309 | // RTLogDestroy(RTLogSetDefaultInstance(NULL));
|
---|
| 310 | #endif
|
---|
| 311 |
|
---|
| 312 | RTSpinlockDestroy(g_Spinlock);
|
---|
| 313 | g_Spinlock = NIL_RTSPINLOCK;
|
---|
| 314 |
|
---|
| 315 | RTR0Term();
|
---|
| 316 | return B_OK;
|
---|
| 317 | }
|
---|
| 318 |
|
---|
[43366] | 319 |
|
---|
[43363] | 320 | /**
|
---|
| 321 | * Interrupt service routine.
|
---|
| 322 | *
|
---|
| 323 | * @returns Whether the interrupt was from VMMDev.
|
---|
| 324 | * @param pvState Opaque pointer to the device state.
|
---|
| 325 | */
|
---|
[58113] | 326 | static int32 vgdrvHaikuISR(void *pvState)
|
---|
[43363] | 327 | {
|
---|
[58113] | 328 | LogFlow((MODULE_NAME ":vgdrvHaikuISR pvState=%p\n", pvState));
|
---|
[43363] | 329 |
|
---|
[58053] | 330 | bool fOurIRQ = VGDrvCommonISR(&g_DevExt);
|
---|
[43410] | 331 | if (fOurIRQ)
|
---|
| 332 | return B_HANDLED_INTERRUPT;
|
---|
| 333 | return B_UNHANDLED_INTERRUPT;
|
---|
[43363] | 334 | }
|
---|
| 335 |
|
---|
[43366] | 336 |
|
---|
[58053] | 337 | void VGDrvNativeISRMousePollEvent(PVBOXGUESTDEVEXT pDevExt)
|
---|
[43363] | 338 | {
|
---|
[58113] | 339 | LogFlow(("VGDrvNativeISRMousePollEvent:\n"));
|
---|
[43363] | 340 |
|
---|
| 341 | status_t err = B_OK;
|
---|
| 342 | //dprintf(MODULE_NAME ": isr mouse\n");
|
---|
| 343 |
|
---|
| 344 | /*
|
---|
| 345 | * Wake up poll waiters.
|
---|
| 346 | */
|
---|
| 347 | //selwakeup(&g_SelInfo);
|
---|
| 348 | //XXX:notify_select_event();
|
---|
| 349 | RTSpinlockAcquire(g_Spinlock);
|
---|
| 350 |
|
---|
[43366] | 351 | if (sState.selectSync)
|
---|
| 352 | {
|
---|
[43363] | 353 | //dprintf(MODULE_NAME ": isr mouse: notify\n");
|
---|
| 354 | notify_select_event(sState.selectSync, sState.selectEvent);
|
---|
| 355 | sState.selectEvent = (uint8_t)0;
|
---|
| 356 | sState.selectRef = (uint32_t)0;
|
---|
| 357 | sState.selectSync = NULL;
|
---|
[43366] | 358 | }
|
---|
| 359 | else
|
---|
[43363] | 360 | err = B_ERROR;
|
---|
| 361 |
|
---|
| 362 | RTSpinlockRelease(g_Spinlock);
|
---|
| 363 | }
|
---|
| 364 |
|
---|
[43366] | 365 |
|
---|
[70066] | 366 | bool VGDrvNativeProcessOption(PVBOXGUESTDEVEXT pDevExt, const char *pszName, const char *pszValue)
|
---|
| 367 | {
|
---|
| 368 | RT_NOREF(pDevExt); RT_NOREF(pszName); RT_NOREF(pszValue);
|
---|
| 369 | return false;
|
---|
| 370 | }
|
---|
| 371 |
|
---|
| 372 |
|
---|
[43363] | 373 | /**
|
---|
| 374 | * Sets IRQ for VMMDev.
|
---|
| 375 | *
|
---|
| 376 | * @returns Haiku error code.
|
---|
| 377 | * @param pvState Pointer to the state info structure.
|
---|
| 378 | */
|
---|
[58113] | 379 | static int vgdrvHaikuAddIRQ(void *pvState)
|
---|
[43363] | 380 | {
|
---|
[43410] | 381 | status_t err;
|
---|
[43363] | 382 | struct VBoxGuestDeviceState *pState = (struct VBoxGuestDeviceState *)pvState;
|
---|
| 383 |
|
---|
[43410] | 384 | AssertReturn(pState, VERR_INVALID_PARAMETER);
|
---|
[43363] | 385 |
|
---|
[58113] | 386 | err = install_io_interrupt_handler(pState->iIrqResId, vgdrvHaikuISR, pState, 0);
|
---|
[43410] | 387 | if (err == B_OK)
|
---|
| 388 | return VINF_SUCCESS;
|
---|
| 389 | return VERR_DEV_IO_ERROR;
|
---|
[43363] | 390 | }
|
---|
| 391 |
|
---|
[43366] | 392 |
|
---|
[43363] | 393 | /**
|
---|
| 394 | * Removes IRQ for VMMDev.
|
---|
| 395 | *
|
---|
| 396 | * @param pvState Opaque pointer to the state info structure.
|
---|
| 397 | */
|
---|
[58113] | 398 | static void vgdrvHaikuRemoveIRQ(void *pvState)
|
---|
[43363] | 399 | {
|
---|
| 400 | struct VBoxGuestDeviceState *pState = (struct VBoxGuestDeviceState *)pvState;
|
---|
[43410] | 401 | AssertPtr(pState);
|
---|
[43363] | 402 |
|
---|
[58113] | 403 | remove_io_interrupt_handler(pState->iIrqResId, vgdrvHaikuISR, pState);
|
---|
[43363] | 404 | }
|
---|
| 405 |
|
---|
[43366] | 406 |
|
---|
[58113] | 407 | static status_t vgdrvHaikuAttach(const pci_info *pDevice)
|
---|
[43363] | 408 | {
|
---|
| 409 | status_t status;
|
---|
[58113] | 410 | int rc;
|
---|
| 411 | int iResId;
|
---|
[43363] | 412 | struct VBoxGuestDeviceState *pState = &sState;
|
---|
[43410] | 413 | static const char *const s_apszGroups[] = VBOX_LOGGROUP_NAMES;
|
---|
| 414 | PRTLOGGER pRelLogger;
|
---|
[43363] | 415 |
|
---|
[43410] | 416 | AssertReturn(pDevice, B_BAD_VALUE);
|
---|
| 417 |
|
---|
[43363] | 418 | cUsers = 0;
|
---|
| 419 |
|
---|
| 420 | /*
|
---|
| 421 | * Initialize IPRT R0 driver, which internally calls OS-specific r0 init.
|
---|
| 422 | */
|
---|
| 423 | rc = RTR0Init(0);
|
---|
| 424 | if (RT_FAILURE(rc))
|
---|
| 425 | {
|
---|
[58113] | 426 | dprintf(MODULE_NAME ": RTR0Init failed: %d\n", rc);
|
---|
[43363] | 427 | return ENXIO;
|
---|
| 428 | }
|
---|
| 429 |
|
---|
[58113] | 430 | rc = RTSpinlockCreate(&g_Spinlock, RTSPINLOCK_FLAGS_INTERRUPT_SAFE, "vgdrvHaiku");
|
---|
[43363] | 431 | if (RT_FAILURE(rc))
|
---|
| 432 | {
|
---|
[58113] | 433 | LogRel(("vgdrvHaikuAttach: RTSpinlock create failed. rc=%Rrc\n", rc));
|
---|
[43366] | 434 | return ENXIO;
|
---|
[43363] | 435 | }
|
---|
| 436 |
|
---|
| 437 | #ifdef DO_LOG
|
---|
| 438 | /*
|
---|
| 439 | * Create the release log.
|
---|
| 440 | * (We do that here instead of common code because we want to log
|
---|
| 441 | * early failures using the LogRel macro.)
|
---|
| 442 | */
|
---|
[43366] | 443 | rc = RTLogCreate(&pRelLogger, 0 | RTLOGFLAGS_PREFIX_THREAD /* fFlags */, "all",
|
---|
[43363] | 444 | "VBOX_RELEASE_LOG", RT_ELEMENTS(s_apszGroups), s_apszGroups,
|
---|
| 445 | RTLOGDEST_STDOUT | RTLOGDEST_DEBUGGER | RTLOGDEST_USER, NULL);
|
---|
[43366] | 446 | dprintf(MODULE_NAME ": RTLogCreate: %d\n", rc);
|
---|
[43363] | 447 | if (RT_SUCCESS(rc))
|
---|
| 448 | {
|
---|
| 449 | //RTLogGroupSettings(pRelLogger, g_szLogGrp);
|
---|
| 450 | //RTLogFlags(pRelLogger, g_szLogFlags);
|
---|
| 451 | //RTLogDestinations(pRelLogger, "/var/log/vboxguest.log");
|
---|
| 452 | RTLogRelSetDefaultInstance(pRelLogger);
|
---|
[43366] | 453 | RTLogSetDefaultInstance(pRelLogger); //XXX
|
---|
[43363] | 454 | }
|
---|
| 455 | #endif
|
---|
| 456 |
|
---|
| 457 | /*
|
---|
| 458 | * Allocate I/O port resource.
|
---|
| 459 | */
|
---|
| 460 | pState->uIOPortBase = pDevice->u.h0.base_registers[0];
|
---|
[63566] | 461 | /** @todo check flags for IO? */
|
---|
[43363] | 462 | if (pState->uIOPortBase)
|
---|
| 463 | {
|
---|
| 464 | /*
|
---|
| 465 | * Map the MMIO region.
|
---|
| 466 | */
|
---|
| 467 | uint32 phys = pDevice->u.h0.base_registers[1];
|
---|
[63566] | 468 | /** @todo Check flags for mem? */
|
---|
[43363] | 469 | pState->VMMDevMemSize = pDevice->u.h0.base_register_sizes[1];
|
---|
[43410] | 470 | pState->iVMMDevMemAreaId = map_physical_memory("VirtualBox Guest MMIO", phys, pState->VMMDevMemSize,
|
---|
| 471 | B_ANY_KERNEL_BLOCK_ADDRESS, B_KERNEL_READ_AREA | B_KERNEL_WRITE_AREA,
|
---|
| 472 | &pState->pMMIOBase);
|
---|
[43363] | 473 | if (pState->iVMMDevMemAreaId > 0 && pState->pMMIOBase)
|
---|
| 474 | {
|
---|
| 475 | /*
|
---|
| 476 | * Call the common device extension initializer.
|
---|
| 477 | */
|
---|
[100267] | 478 | rc = VGDrvCommonInitDevExt(&g_DevExt, pState->uIOPortBase, NULL /*pvMmioReq*/,
|
---|
| 479 | pState->pMMIOBase, pState->VMMDevMemSize,
|
---|
[43363] | 480 | #if ARCH_BITS == 64
|
---|
[58053] | 481 | VBOXOSTYPE_Haiku_x64,
|
---|
[43363] | 482 | #else
|
---|
[58053] | 483 | VBOXOSTYPE_Haiku,
|
---|
[43363] | 484 | #endif
|
---|
[58053] | 485 | VMMDEV_EVENT_MOUSE_POSITION_CHANGED);
|
---|
[43363] | 486 | if (RT_SUCCESS(rc))
|
---|
| 487 | {
|
---|
| 488 | /*
|
---|
| 489 | * Add IRQ of VMMDev.
|
---|
| 490 | */
|
---|
| 491 | pState->iIrqResId = pDevice->u.h0.interrupt_line;
|
---|
[58113] | 492 | rc = vgdrvHaikuAddIRQ(pState);
|
---|
[43363] | 493 | if (RT_SUCCESS(rc))
|
---|
| 494 | {
|
---|
[70088] | 495 | /*
|
---|
| 496 | * Read host configuration.
|
---|
| 497 | */
|
---|
| 498 | VGDrvCommonProcessOptionsFromHost(&g_DevExt);
|
---|
| 499 |
|
---|
[43410] | 500 | LogRel((MODULE_NAME ": loaded successfully\n"));
|
---|
| 501 | return B_OK;
|
---|
[43363] | 502 | }
|
---|
[43410] | 503 |
|
---|
[58113] | 504 | LogRel((MODULE_NAME ": VGDrvCommonInitDevExt failed.\n"));
|
---|
[58053] | 505 | VGDrvCommonDeleteDevExt(&g_DevExt);
|
---|
[43363] | 506 | }
|
---|
| 507 | else
|
---|
[58113] | 508 | LogRel((MODULE_NAME ": vgdrvHaikuAddIRQ failed.\n"));
|
---|
[43363] | 509 | }
|
---|
| 510 | else
|
---|
[58113] | 511 | LogRel((MODULE_NAME ": MMIO region setup failed.\n"));
|
---|
[43363] | 512 | }
|
---|
| 513 | else
|
---|
[58113] | 514 | LogRel((MODULE_NAME ": IOport setup failed.\n"));
|
---|
[43363] | 515 |
|
---|
| 516 | RTR0Term();
|
---|
| 517 | return ENXIO;
|
---|
| 518 | }
|
---|
| 519 |
|
---|
[43366] | 520 |
|
---|
[58113] | 521 | static status_t vgdrvHaikuProbe(pci_info *pDevice)
|
---|
[43363] | 522 | {
|
---|
[58113] | 523 | if ( pDevice->vendor_id == VMMDEV_VENDORID
|
---|
| 524 | && pDevice->device_id == VMMDEV_DEVICEID)
|
---|
[43410] | 525 | return B_OK;
|
---|
[43363] | 526 |
|
---|
| 527 | return ENXIO;
|
---|
| 528 | }
|
---|
| 529 |
|
---|
[43366] | 530 |
|
---|
[43363] | 531 | status_t init_module(void)
|
---|
| 532 | {
|
---|
[43410] | 533 | status_t err = B_ENTRY_NOT_FOUND;
|
---|
[43363] | 534 | pci_info info;
|
---|
| 535 | int ix = 0;
|
---|
| 536 |
|
---|
[43411] | 537 | err = get_module(B_PCI_MODULE_NAME, (module_info **)&gPCI);
|
---|
| 538 | if (err != B_OK)
|
---|
| 539 | return err;
|
---|
[43363] | 540 |
|
---|
[43366] | 541 | while ((*gPCI->get_nth_pci_info)(ix++, &info) == B_OK)
|
---|
| 542 | {
|
---|
[58113] | 543 | if (vgdrvHaikuProbe(&info) == 0)
|
---|
[43366] | 544 | {
|
---|
[43411] | 545 | /* We found it */
|
---|
[58113] | 546 | err = vgdrvHaikuAttach(&info);
|
---|
[43411] | 547 | return err;
|
---|
[43363] | 548 | }
|
---|
| 549 | }
|
---|
| 550 |
|
---|
[43411] | 551 | return B_ENTRY_NOT_FOUND;
|
---|
[43363] | 552 | }
|
---|
| 553 |
|
---|
[43366] | 554 |
|
---|
[43363] | 555 | void uninit_module(void)
|
---|
| 556 | {
|
---|
[58113] | 557 | vgdrvHaikuDetach();
|
---|
[43363] | 558 | put_module(B_PCI_MODULE_NAME);
|
---|
| 559 | }
|
---|
| 560 |
|
---|
[43366] | 561 |
|
---|
| 562 | static status_t std_ops(int32 op, ...)
|
---|
| 563 | {
|
---|
| 564 | switch (op)
|
---|
| 565 | {
|
---|
| 566 | case B_MODULE_INIT:
|
---|
| 567 | return init_module();
|
---|
[43411] | 568 |
|
---|
[43366] | 569 | case B_MODULE_UNINIT:
|
---|
[43411] | 570 | {
|
---|
[43366] | 571 | uninit_module();
|
---|
| 572 | return B_OK;
|
---|
[43411] | 573 | }
|
---|
| 574 |
|
---|
[43366] | 575 | default:
|
---|
| 576 | return B_ERROR;
|
---|
[43363] | 577 | }
|
---|
| 578 | }
|
---|
| 579 |
|
---|
[43366] | 580 |
|
---|
| 581 | _EXPORT module_info *modules[] =
|
---|
| 582 | {
|
---|
| 583 | (module_info *)&g_VBoxGuest,
|
---|
[43363] | 584 | NULL
|
---|
| 585 | };
|
---|
| 586 |
|
---|
| 587 | /* Common code that depend on g_DevExt. */
|
---|
| 588 | #include "VBoxGuestIDC-unix.c.h"
|
---|
[43366] | 589 |
|
---|