/*
Copyright 2006-2008, V.
For contact information, see http://winaoe.org/
This file is part of WinAoE.
WinAoE is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
WinAoE is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with WinAoE. If not, see <http://www.gnu.org/licenses/>.
*/
#include "portable.h"
#include <stdio.h>
#include <ntddk.h>
#include <srb.h>
#include <scsi.h>
#include <ntddscsi.h>
#include <ntddstor.h>
#include <ntdddisk.h>
#include <initguid.h>
#include "driver.h"
#include "aoe.h"
#ifndef _MSC_VER
long long __divdi3(long long u, long long v) {return u / v;}
#endif
#ifdef _MSC_VER
#if _WIN32_WINNT <= 0x0500
#ifdef _MSC_VER
#pragma pack(1)
#endif
typedef union _EIGHT_BYTE {
struct {
UCHAR Byte0;
UCHAR Byte1;
UCHAR Byte2;
UCHAR Byte3;
UCHAR Byte4;
UCHAR Byte5;
UCHAR Byte6;
UCHAR Byte7;
};
ULONGLONG AsULongLong;
} __attribute__((__packed__)) EIGHT_BYTE, *PEIGHT_BYTE;
#ifdef _MSC_VER
#pragma pack()
#endif
#define REVERSE_BYTES_QUAD(Destination, Source) { \
PEIGHT_BYTE d = (PEIGHT_BYTE)(Destination); \
PEIGHT_BYTE s = (PEIGHT_BYTE)(Source); \
d->Byte7 = s->Byte0; \
d->Byte6 = s->Byte1; \
d->Byte5 = s->Byte2; \
d->Byte4 = s->Byte3; \
d->Byte3 = s->Byte4; \
d->Byte2 = s->Byte5; \
d->Byte1 = s->Byte6; \
d->Byte0 = s->Byte7; \
}
#endif
#endif
#if _WIN32_WINNT < 0x0502
#ifdef _MSC_VER
#pragma pack(1)
#endif
typedef struct _READ_CAPACITY_DATA_EX {
LARGE_INTEGER LogicalBlockAddress;
ULONG BytesPerBlock;
} __attribute__((__packed__)) READ_CAPACITY_DATA_EX, *PREAD_CAPACITY_DATA_EX;
#ifdef _MSC_VER
#pragma pack()
#endif
#endif
#ifdef _MSC_VER
#pragma pack(1)
#endif
typedef struct _PORTABLE_CDB16 {
UCHAR OperationCode;
UCHAR Reserved1:3;
UCHAR ForceUnitAccess:1;
UCHAR DisablePageOut:1;
UCHAR Protection:3;
UCHAR LogicalBlock[8];
UCHAR TransferLength[4];
UCHAR Reserved2;
UCHAR Control;
} __attribute__((__packed__)) CDB16, *PCDB16;
#ifdef _MSC_VER
#pragma pack()
#endif
DEFINE_GUID(GUID_BUS_TYPE_INTERNAL, 0x2530ea73L, 0x086b, 0x11d1, 0xa0, 0x9f, 0x00, 0xc0, 0x4f, 0xc3, 0x40, 0xb1);
// in this file
NTSTATUS STDCALL BusGetDeviceCapabilities(IN PDEVICE_OBJECT DeviceObject, IN PDEVICE_CAPABILITIES DeviceCapabilities);
NTSTATUS STDCALL DiskDispatchPnP(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN PIO_STACK_LOCATION Stack, IN PDEVICEEXTENSION DeviceExtension) {
NTSTATUS Status;
PDEVICE_RELATIONS DeviceRelations;
PPNP_BUS_INFORMATION PnPBusInformation;
PDEVICE_CAPABILITIES DeviceCapabilities;
DEVICE_CAPABILITIES ParentDeviceCapabilities;
PWCHAR String;
ULONG StringLength;
switch (Stack->MinorFunction) {
case IRP_MN_QUERY_ID:
if ((String = (PWCHAR)ExAllocatePool(NonPagedPool, (512 * sizeof(WCHAR)))) == NULL) {
DbgPrint("DiskDispatchPnP ExAllocatePool IRP_MN_QUERY_ID\n");
Status = STATUS_INSUFFICIENT_RESOURCES;
break;
}
RtlZeroMemory(String, (512 * sizeof(WCHAR)));
switch (Stack->Parameters.QueryId.IdType) {
case BusQueryDeviceID:
StringLength = swprintf(String, L"AoE\\Disk%lu", DeviceExtension->Disk.DiskNumber) + 1;
if ((Irp->IoStatus.Information = (ULONG_PTR)ExAllocatePool(PagedPool, StringLength * sizeof(WCHAR))) == 0) {
DbgPrint("DiskDispatchPnP ExAllocatePool BusQueryDeviceID\n");
Status = STATUS_INSUFFICIENT_RESOURCES;
break;
}
RtlCopyMemory((PWCHAR)Irp->IoStatus.Information, String, StringLength * sizeof(WCHAR));
Status = STATUS_SUCCESS;
break;
case BusQueryInstanceID:
StringLength = swprintf(String, L"AOEDISK%lu", DeviceExtension->Disk.DiskNumber) + 1;
if ((Irp->IoStatus.Information = (ULONG_PTR)ExAllocatePool(PagedPool, StringLength * sizeof(WCHAR))) == 0) {
DbgPrint("DiskDispatchPnP ExAllocatePool BusQueryInstanceID\n");
Status = STATUS_INSUFFICIENT_RESOURCES;
break;
}
RtlCopyMemory((PWCHAR)Irp->IoStatus.Information, String, StringLength * sizeof(WCHAR));
Status = STATUS_SUCCESS;
break;
case BusQueryHardwareIDs:
StringLength = swprintf(String, L"AoE\\Disk%lu", DeviceExtension->Disk.DiskNumber) + 1;
StringLength += swprintf(&String[StringLength], L"GenDisk") + 4;
if ((Irp->IoStatus.Information = (ULONG_PTR)ExAllocatePool(PagedPool, StringLength * sizeof(WCHAR))) == 0) {
DbgPrint("DiskDispatchPnP ExAllocatePool BusQueryHardwareIDs\n");
Status = STATUS_INSUFFICIENT_RESOURCES;
break;
}
RtlCopyMemory((PWCHAR)Irp->IoStatus.Information, String, StringLength * sizeof(WCHAR));
Status = STATUS_SUCCESS;
break;
case BusQueryCompatibleIDs:
StringLength = swprintf(String, L"GenDisk") + 4;
if ((Irp->IoStatus.Information = (ULONG_PTR)ExAllocatePool(PagedPool, StringLength * sizeof(WCHAR))) == 0) {
DbgPrint("DiskDispatchPnP ExAllocatePool BusQueryCompatibleIDs\n");
Status = STATUS_INSUFFICIENT_RESOURCES;
break;
}
RtlCopyMemory((PWCHAR)Irp->IoStatus.Information, String, StringLength * sizeof(WCHAR));
Status = STATUS_SUCCESS;
break;
default:
Irp->IoStatus.Information = 0;
Status = STATUS_NOT_SUPPORTED;
}
ExFreePool(String);
break;
case IRP_MN_QUERY_DEVICE_TEXT:
if ((String = (PWCHAR)ExAllocatePool(NonPagedPool, (512 * sizeof(WCHAR)))) == NULL) {
DbgPrint("DiskDispatchPnP ExAllocatePool IRP_MN_QUERY_DEVICE_TEXT\n");
Status = STATUS_INSUFFICIENT_RESOURCES;
break;
}
RtlZeroMemory(String, (512 * sizeof(WCHAR)));
switch (Stack->Parameters.QueryDeviceText.DeviceTextType ) {
case DeviceTextDescription:
StringLength = swprintf(String, L"AoE Disk") + 1;
if ((Irp->IoStatus.Information = (ULONG_PTR)ExAllocatePool(PagedPool, StringLength * sizeof(WCHAR))) == 0) {
DbgPrint("DiskDispatchPnP ExAllocatePool DeviceTextDescription\n");
Status = STATUS_INSUFFICIENT_RESOURCES;
break;
}
RtlCopyMemory((PWCHAR)Irp->IoStatus.Information, String, StringLength * sizeof(WCHAR));
Status = STATUS_SUCCESS;
break;
case DeviceTextLocationInformation:
StringLength = swprintf(String, L"AoE e%d.%d", DeviceExtension->Disk.Major, DeviceExtension->Disk.Minor) + 1;
if ((Irp->IoStatus.Information = (ULONG_PTR)ExAllocatePool(PagedPool, StringLength * sizeof(WCHAR))) == 0) {
DbgPrint("DiskDispatchPnP ExAllocatePool DeviceTextLocationInformation\n");
Status = STATUS_INSUFFICIENT_RESOURCES;
break;
}
RtlCopyMemory((PWCHAR)Irp->IoStatus.Information, String, StringLength * sizeof(WCHAR));
Status = STATUS_SUCCESS;
break;
default:
Irp->IoStatus.Information = 0;
Status = STATUS_NOT_SUPPORTED;
}
ExFreePool(String);
break;
case IRP_
评论0