NTLegacy.cpp revision e64031e20c39650a7bc902a3e1aba613b9415dee
/** @file
*
* VBoxGuest -- VirtualBox Win32 guest support driver
*
* Copyright (C) 2006-2007 Oracle Corporation
*
* This file is part of VirtualBox Open Source Edition (OSE), as
* available from http://www.virtualbox.org. This file is free software;
* General Public License (GPL) as published by the Free Software
* Foundation, in version 2 as it comes in the "COPYING" file of the
* VirtualBox OSE distribution. VirtualBox OSE is distributed in the
* hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
*/
// enable backdoor logging
//#define LOG_ENABLED
/*******************************************************************************
* Header Files *
*******************************************************************************/
#include "NTLegacy.h"
#include "Helper.h"
#include <VBox/VBoxGuestLib.h>
/*******************************************************************************
* Defined Constants And Macros *
*******************************************************************************/
/*******************************************************************************
* Internal Functions *
*******************************************************************************/
extern "C"
{
}
#ifdef ALLOC_PRAGMA
#endif
/**
* Helper function to create the device object
*
* @returns NT status code
* @param
*/
{
dprintf(("VBoxGuest::ntCreateDevice: entered, pDrvObj=%x, pDevObj=%x, pRegPath=%x\n",
/*
* Find our virtual PCI device
*/
if (!NT_SUCCESS(rc))
{
dprintf(("VBoxGuest::createDevice: device not found, returning\n"));
return rc;
}
/*
* Create device.
*/
rc = IoCreateDevice(pDrvObj, sizeof(VBOXGUESTDEVEXT), &DevName, FILE_DEVICE_UNKNOWN, 0, FALSE, &deviceObject);
if (!NT_SUCCESS(rc))
{
return rc;
}
dprintf(("VBoxGuest::ntCreateDevice: device created\n"));
if (!NT_SUCCESS(rc))
{
return rc;
}
dprintf(("VBoxGuest::ntCreateDevice: symlink created\n"));
/*
* Setup the device extension.
*/
if (pDevObj) /* pDevObj always is NULL at the moment, so don't attach to the driver stack */
{
{
dprintf(("VBoxGuest::ntCreateDevice: IoAttachDeviceToDeviceStack did not give a nextLowerDrive\n"));
return STATUS_NO_SUCH_DEVICE;
}
dprintf(("VBoxGuest::ntCreateDevice: device attached to stack\n"));
}
#ifdef VBOX_WITH_HGCM
/* Create global spinlock for all driver sessions */
if (RT_FAILURE(rc2))
{
dprintf(("VBoxGuest::ntCreateDevice: RTSpinlockCreate failed\n"));
return STATUS_DRIVER_UNABLE_TO_LOAD;
}
dprintf(("VBoxGuest::ntCreateDevice: spinlock created\n"));
#endif
/* Store a reference to ourself */
/* Store bus and slot number we've queried before */
#endif
//
// let's have a look at what our PCI adapter offers
//
dprintf(("VBoxGuest::ntCreateDevice: starting to scan PCI resources of VBoxGuest\n"));
// assign the PCI resources
&resourceList);
if (!NT_SUCCESS(rc))
{
return rc;
}
if (!RT_SUCCESS(rc))
{
}
rc = VbglGRAlloc ((VMMDevRequestHeader **)&pDevExt->irqAckEvents, sizeof (VMMDevEvents), VMMDevReq_AcknowledgeEvents);
if (!RT_SUCCESS(rc))
{
}
rc = VbglGRAlloc ((VMMDevRequestHeader **)&pDevExt->powerStateRequest, sizeof (VMMDevPowerStateRequest), VMMDevReq_SetPowerStatus);
if (!RT_SUCCESS(rc))
{
}
#if 0
//
// now proceed to the busmaster DMA stuff
//
{
dprintf(("VBoxGuest::ntCreateDevice: HalGetAdapter failed!\n"));
return rc;
}
// @todo allocate S/G buffer
#endif
//
// it's time to map the I/O and memory spaces
//
// Map physical address of VMMDev memory
if (!NT_SUCCESS(rc))
{
return rc;
}
//
// now we need an ISR and DPC
//
// register DPC routine
dprintf(("VBoxGuest::ntCreateDevice: initializing DPC...\n"));
// get an interrupt vector
// only proceed if the device provides an interrupt
{
&irql,
&affinity);
pDevExt, // context
NULL, // optional spinlock
vector, // interrupt vector
irql, // interrupt level
irql, // interrupt level
TRUE, // shareable interrupt
affinity, // CPU affinity
FALSE); // don't save FPU stack
if (!NT_SUCCESS(rc))
{
return rc;
}
dprintf(("VBoxGuest::ntCreateDevice: IRQ connected!\n"));
}
if (NT_SUCCESS(rc))
{
// create our thread to inform the VBoxMouse driver
}
if (NT_SUCCESS(rc))
{
// initialize the event notification semaphore
/* Preallocated constant timeout 250ms for HGCM async waiter. */
}
if (!NT_SUCCESS(rc))
{
return STATUS_UNSUCCESSFUL;
}
/** @todo cleanup on failure */
// ready to rumble!
return rc;
}
/**
* Helper function to handle the PCI device lookup
*
* @returns NT error codes
*/
{
dprintf(("findPCIDevice\n"));
slotNumber.u.AsULONG = 0;
// scan each bus
{
// scan each device
{
// scan each function (not really required...)
{
// have a look at what's in this slot
{
// no such bus, we're done with it
break;
}
{
// we have to proceed to the next function
continue;
}
// check if it's another device
{
continue;
}
// Hooray, we've found it!
dprintf(("device found!\n"));
*pBusNumber = busNumber;
rc = STATUS_SUCCESS;
}
}
}
return rc;
}
/**
* Helper function to cleanup resources
*
* @param pDrvObj Driver object.
* @param pDevObj Device object.
*/
{
// if there's no device extension, we're screwed
if (!pDevExt)
{
dprintf(("freeDeviceResources: FATAL ERROR! device extension pointer is NULL! Not freeing resources!\n"));
return;
}
// indicate that the device is no longer ready
// disconnect interrupts
if (pDevExt->interruptObject)
{
}
}