ReactOS 0.4.15-dev-7693-gd0e2924
diskwmi.c File Reference
#include "disk.h"
Include dependency graph for diskwmi.c:

Go to the source code of this file.

Macros

#define DiskGeometryGuid   0
 
#define SmartStatusGuid   1
 
#define SmartDataGuid   2
 
#define SmartPerformFunction   3
 
#define AllowDisallowPerformanceHit   1
 
#define EnableDisableHardwareFailurePrediction   2
 
#define EnableDisableFailurePredictionPolling   3
 
#define GetFailurePredictionCapability   4
 
#define EnableOfflineDiags   5
 
#define SmartEventGuid   4
 
#define SmartThresholdsGuid   5
 
#define ScsiInfoExceptionsGuid   6
 
#define DiskReadSmartData(FdoExtension, SrbControl, BufferSize)
 
#define DiskReadSmartThresholds(FdoExtension, SrbControl, BufferSize)
 
#define DiskReadSmartStatus(FdoExtension, SrbControl, BufferSize)
 
#define DiskGetIdentifyData(FdoExtension, SrbControl, BufferSize)
 

Functions

NTSTATUS DiskSendFailurePredictIoctl (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, PSTORAGE_PREDICT_FAILURE checkFailure)
 
NTSTATUS DiskGetIdentifyInfo (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, PBOOLEAN SupportSmart)
 
NTSTATUS DiskDetectFailurePrediction (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, PFAILURE_PREDICTION_METHOD FailurePredictCapability, BOOLEAN ScsiAddressAvailable)
 
NTSTATUS DiskReadFailurePredictThresholds (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, PSTORAGE_FAILURE_PREDICT_THRESHOLDS DiskSmartThresholds)
 
NTSTATUS DiskReadSmartLog (IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, IN UCHAR SectorCount, IN UCHAR LogAddress, OUT PUCHAR Buffer)
 
NTSTATUS DiskWriteSmartLog (IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, IN UCHAR SectorCount, IN UCHAR LogAddress, IN PUCHAR Buffer)
 
static NTSTATUS DiskEnableSmart (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension)
 
static NTSTATUS DiskDisableSmart (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension)
 
_inline NTSTATUS DiskEnableSmartAttributeAutosave (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension)
 
_inline NTSTATUS DiskDisableSmartAttributeAutosave (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension)
 
static NTSTATUS DiskExecuteSmartDiagnostics (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, UCHAR Subcommand)
 
NTSTATUS DiskPerformSmartCommand (IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, IN ULONG SrbControlCode, IN UCHAR Command, IN UCHAR Feature, IN UCHAR SectorCount, IN UCHAR SectorNumber, IN OUT PSRB_IO_CONTROL SrbControl, OUT PULONG BufferSize)
 
NTSTATUS DiskGetModePage (_In_ PDEVICE_OBJECT Fdo, _In_ UCHAR PageMode, _In_ UCHAR PageControl, _In_ PMODE_PARAMETER_HEADER ModeData, _Inout_ PULONG ModeDataSize, _Out_ PVOID *PageData)
 
NTSTATUS DiskEnableInfoExceptions (_In_ PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, _In_ BOOLEAN Enable)
 
NTSTATUS DiskEnableDisableFailurePrediction (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, BOOLEAN Enable)
 
NTSTATUS DiskEnableDisableFailurePredictPolling (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, BOOLEAN Enable, ULONG PollTimeInSeconds)
 
NTSTATUS DiskReadFailurePredictStatus (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, PSTORAGE_FAILURE_PREDICT_STATUS DiskSmartStatus)
 
NTSTATUS DiskReadFailurePredictData (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, PSTORAGE_FAILURE_PREDICT_DATA DiskSmartData)
 
VOID NTAPI DiskReregWorker (IN PDEVICE_OBJECT DevObject, IN PVOID Context)
 
NTSTATUS DiskInitializeReregistration (VOID)
 
NTSTATUS DiskPostReregisterRequest (PDEVICE_OBJECT DeviceObject, PIRP Irp)
 
NTSTATUS NTAPI DiskInfoExceptionComplete (PDEVICE_OBJECT DeviceObject, PIRP Irp, PVOID Context)
 
NTSTATUS DiskInfoExceptionCheck (PFUNCTIONAL_DEVICE_EXTENSION FdoExtension)
 
NTSTATUS NTAPI DiskWmiFunctionControl (IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN ULONG GuidIndex, IN CLASSENABLEDISABLEFUNCTION Function, IN BOOLEAN Enable)
 
NTSTATUS NTAPI DiskFdoQueryWmiRegInfo (IN PDEVICE_OBJECT DeviceObject, OUT ULONG *RegFlags, OUT PUNICODE_STRING InstanceName)
 
NTSTATUS NTAPI DiskFdoQueryWmiRegInfoEx (IN PDEVICE_OBJECT DeviceObject, OUT ULONG *RegFlags, OUT PUNICODE_STRING InstanceName, OUT PUNICODE_STRING MofName)
 
NTSTATUS NTAPI DiskFdoQueryWmiDataBlock (IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN ULONG GuidIndex, IN ULONG BufferAvail, OUT PUCHAR Buffer)
 
NTSTATUS NTAPI DiskFdoSetWmiDataBlock (IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN ULONG GuidIndex, IN ULONG BufferSize, IN PUCHAR Buffer)
 
NTSTATUS NTAPI DiskFdoSetWmiDataItem (IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN ULONG GuidIndex, IN ULONG DataItemId, IN ULONG BufferSize, IN PUCHAR Buffer)
 
NTSTATUS NTAPI DiskFdoExecuteWmiMethod (IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN ULONG GuidIndex, IN ULONG MethodId, IN ULONG InBufferSize, IN ULONG OutBufferSize, IN PUCHAR Buffer)
 

Variables

IO_WORKITEM_ROUTINE DiskReregWorker
 
IO_COMPLETION_ROUTINE DiskInfoExceptionComplete
 
SINGLE_LIST_ENTRY DiskReregHead
 
KSPIN_LOCK DiskReregSpinlock
 
LONG DiskReregWorkItems
 
GUIDREGINFO DiskWmiFdoGuidList []
 
GUID DiskPredictFailureEventGuid = WMI_STORAGE_PREDICT_FAILURE_EVENT_GUID
 

Macro Definition Documentation

◆ AllowDisallowPerformanceHit

#define AllowDisallowPerformanceHit   1

Definition at line 144 of file diskwmi.c.

◆ DiskGeometryGuid

#define DiskGeometryGuid   0

Definition at line 140 of file diskwmi.c.

◆ DiskGetIdentifyData

#define DiskGetIdentifyData (   FdoExtension,
  SrbControl,
  BufferSize 
)
Value:
ID_CMD, \
0, \
0, \
0, \
(SrbControl), \
#define ID_CMD
Definition: helper.h:20
#define IOCTL_SCSI_MINIPORT_IDENTIFY
Definition: cdrw_hw.h:1458
NTSTATUS DiskPerformSmartCommand(IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, IN ULONG SrbControlCode, IN UCHAR Command, IN UCHAR Feature, IN UCHAR SectorCount, IN UCHAR SectorNumber, IN OUT PSRB_IO_CONTROL SrbControl, OUT PULONG BufferSize)
Definition: diskwmi.c:476
@ FdoExtension
Definition: precomp.h:48
_In_ WDFMEMORY _Out_opt_ size_t * BufferSize
Definition: wdfmemory.h:254

Definition at line 254 of file diskwmi.c.

◆ DiskReadSmartData

#define DiskReadSmartData (   FdoExtension,
  SrbControl,
  BufferSize 
)
Value:
0, \
0, \
(SrbControl), \
#define SMART_CMD
Definition: helper.h:21
#define IOCTL_SCSI_MINIPORT_READ_SMART_ATTRIBS
Definition: cdrw_hw.h:1459
#define READ_ATTRIBUTES
Definition: ntdddisk.h:744

Definition at line 200 of file diskwmi.c.

◆ DiskReadSmartStatus

#define DiskReadSmartStatus (   FdoExtension,
  SrbControl,
  BufferSize 
)
Value:
0, \
0, \
(SrbControl), \
#define IOCTL_SCSI_MINIPORT_RETURN_STATUS
Definition: cdrw_hw.h:1463
#define RETURN_SMART_STATUS
Definition: ntdddisk.h:753

Definition at line 236 of file diskwmi.c.

◆ DiskReadSmartThresholds

#define DiskReadSmartThresholds (   FdoExtension,
  SrbControl,
  BufferSize 
)
Value:
0, \
0, \
(SrbControl), \
#define IOCTL_SCSI_MINIPORT_READ_SMART_THRESHOLDS
Definition: cdrw_hw.h:1460
#define READ_THRESHOLDS
Definition: ntdddisk.h:745

Definition at line 218 of file diskwmi.c.

◆ EnableDisableFailurePredictionPolling

#define EnableDisableFailurePredictionPolling   3

Definition at line 146 of file diskwmi.c.

◆ EnableDisableHardwareFailurePrediction

#define EnableDisableHardwareFailurePrediction   2

Definition at line 145 of file diskwmi.c.

◆ EnableOfflineDiags

#define EnableOfflineDiags   5

Definition at line 148 of file diskwmi.c.

◆ GetFailurePredictionCapability

#define GetFailurePredictionCapability   4

Definition at line 147 of file diskwmi.c.

◆ ScsiInfoExceptionsGuid

#define ScsiInfoExceptionsGuid   6

Definition at line 152 of file diskwmi.c.

◆ SmartDataGuid

#define SmartDataGuid   2

Definition at line 142 of file diskwmi.c.

◆ SmartEventGuid

#define SmartEventGuid   4

Definition at line 150 of file diskwmi.c.

◆ SmartPerformFunction

#define SmartPerformFunction   3

Definition at line 143 of file diskwmi.c.

◆ SmartStatusGuid

#define SmartStatusGuid   1

Definition at line 141 of file diskwmi.c.

◆ SmartThresholdsGuid

#define SmartThresholdsGuid   5

Definition at line 151 of file diskwmi.c.

Function Documentation

◆ DiskDetectFailurePrediction()

NTSTATUS DiskDetectFailurePrediction ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
PFAILURE_PREDICTION_METHOD  FailurePredictCapability,
BOOLEAN  ScsiAddressAvailable 
)

Definition at line 2230 of file diskwmi.c.

2270{
2272 PDISK_DATA diskData = (PDISK_DATA)(commonExtension->DriverData);
2273 BOOLEAN supportFP;
2275 STORAGE_PREDICT_FAILURE checkFailure;
2276 STORAGE_FAILURE_PREDICT_STATUS diskSmartStatus;
2277
2278 PAGED_CODE();
2279
2280 //
2281 // Assume no failure predict mechanisms
2282 //
2283 *FailurePredictCapability = FailurePredictionNone;
2284
2285 //
2286 // See if this is an IDE drive that supports SMART. If so enable SMART
2287 // and then ensure that it suports the SMART READ STATUS command
2288 //
2289
2290 if (ScsiAddressAvailable)
2291 {
2292 DiskGetIdentifyInfo(FdoExtension, &supportFP);
2293
2294 if (supportFP)
2295 {
2297 if (NT_SUCCESS(status))
2298 {
2299 *FailurePredictCapability = FailurePredictionSmart;
2300 diskData->FailurePredictionEnabled = TRUE;
2301
2303 &diskSmartStatus);
2304
2305 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: Device %p %s IDE SMART\n",
2306 FdoExtension->DeviceObject,
2307 NT_SUCCESS(status) ? "does" : "does not"));
2308
2309 if (!NT_SUCCESS(status))
2310 {
2311 *FailurePredictCapability = FailurePredictionNone;
2312 diskData->FailurePredictionEnabled = FALSE;
2313 }
2314 }
2315 return(status);
2316 }
2317 }
2318 //
2319 // See if there is a a filter driver to intercept
2320 // IOCTL_STORAGE_PREDICT_FAILURE
2321 //
2323 &checkFailure);
2324
2325 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: Device %p %s IOCTL_STORAGE_FAILURE_PREDICT\n",
2326 FdoExtension->DeviceObject,
2327 NT_SUCCESS(status) ? "does" : "does not"));
2328
2329 if (NT_SUCCESS(status))
2330 {
2331 *FailurePredictCapability = FailurePredictionIoctl;
2332 diskData->FailurePredictionEnabled = TRUE;
2333 if (checkFailure.PredictFailure)
2334 {
2335 checkFailure.PredictFailure = 512;
2336 ClassNotifyFailurePredicted(FdoExtension,
2337 (PUCHAR)&checkFailure,
2338 sizeof(checkFailure),
2339 (BOOLEAN)(FdoExtension->FailurePredicted == FALSE),
2340 0x11,
2341 diskData->ScsiAddress.PathId,
2342 diskData->ScsiAddress.TargetId,
2343 diskData->ScsiAddress.Lun);
2344
2345 FdoExtension->FailurePredicted = TRUE;
2346 }
2347 return(status);
2348 }
2349
2350 //
2351 // Finally we assume it will not be a scsi smart drive. but
2352 // we'll also send off an asynchronous mode sense so that if
2353 // it is SMART we'll reregister the device object
2354 //
2355
2356 *FailurePredictCapability = FailurePredictionNone;
2357
2359
2360 return(STATUS_SUCCESS);
2361}
#define PAGED_CODE()
unsigned char BOOLEAN
LONG NTSTATUS
Definition: precomp.h:26
@ FailurePredictionSmart
Definition: classpnp.h:236
@ FailurePredictionNone
Definition: classpnp.h:234
@ FailurePredictionIoctl
Definition: classpnp.h:235
NTSTATUS DiskSendFailurePredictIoctl(PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, PSTORAGE_PREDICT_FAILURE checkFailure)
Definition: diskwmi.c:854
static NTSTATUS DiskEnableSmart(PFUNCTIONAL_DEVICE_EXTENSION FdoExtension)
Definition: diskwmi.c:271
NTSTATUS DiskInfoExceptionCheck(PFUNCTIONAL_DEVICE_EXTENSION FdoExtension)
Definition: diskwmi.c:1922
NTSTATUS DiskGetIdentifyInfo(PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, PBOOLEAN SupportSmart)
Definition: diskwmi.c:813
NTSTATUS DiskReadFailurePredictStatus(PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, PSTORAGE_FAILURE_PREDICT_STATUS DiskSmartStatus)
Definition: diskwmi.c:1251
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
struct _COMMON_DEVICE_EXTENSION * PCOMMON_DEVICE_EXTENSION
struct _DISK_DATA * PDISK_DATA
#define STATUS_SUCCESS
Definition: shellext.h:65
#define TRACE_LEVEL_INFORMATION
Definition: storswtr.h:29
BOOLEAN FailurePredictionEnabled
Definition: disk.h:346
SCSI_ADDRESS ScsiAddress
Definition: disk.h:325
UCHAR PathId
Definition: scsi_port.h:149
UCHAR TargetId
Definition: scsi_port.h:150
Definition: ps.c:97
unsigned char * PUCHAR
Definition: typedefs.h:53

Referenced by DiskInitFdo().

◆ DiskDisableSmart()

static NTSTATUS DiskDisableSmart ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension)
static

Definition at line 293 of file diskwmi.c.

296{
297 UCHAR srbControl[sizeof(SRB_IO_CONTROL) + sizeof(SENDCMDINPARAMS)] = {0};
298 ULONG bufferSize = sizeof(srbControl);
299
302 SMART_CMD,
304 0,
305 0,
306 (PSRB_IO_CONTROL)srbControl,
307 &bufferSize);
308}
#define IOCTL_SCSI_MINIPORT_DISABLE_SMART
Definition: cdrw_hw.h:1462
size_t bufferSize
#define DISABLE_SMART
Definition: ntdddisk.h:752
struct _SRB_IO_CONTROL SRB_IO_CONTROL
uint32_t ULONG
Definition: typedefs.h:59
unsigned char UCHAR
Definition: xmlstorage.h:181

Referenced by DiskEnableDisableFailurePrediction().

◆ DiskDisableSmartAttributeAutosave()

_inline NTSTATUS DiskDisableSmartAttributeAutosave ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension)

Definition at line 337 of file diskwmi.c.

340{
341 UCHAR srbControl[sizeof(SRB_IO_CONTROL) + sizeof(SENDCMDINPARAMS)] = {0};
342 ULONG bufferSize = sizeof(srbControl);
343
346 SMART_CMD,
348 0x00,
349 0,
350 (PSRB_IO_CONTROL)srbControl,
351 &bufferSize);
352}
#define IOCTL_SCSI_MINIPORT_ENABLE_DISABLE_AUTOSAVE
Definition: cdrw_hw.h:1464
#define ENABLE_DISABLE_AUTOSAVE
Definition: ntdddisk.h:746

◆ DiskEnableDisableFailurePrediction()

NTSTATUS DiskEnableDisableFailurePrediction ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
BOOLEAN  Enable 
)

Definition at line 1126 of file diskwmi.c.

1147{
1149 PCOMMON_DEVICE_EXTENSION commonExtension = &(FdoExtension->CommonExtension);
1150 PDISK_DATA diskData = (PDISK_DATA)(commonExtension->DriverData);
1151
1152 PAGED_CODE();
1153
1154 switch(diskData->FailurePredictionCapability)
1155 {
1157 {
1158 if (Enable)
1159 {
1161 } else {
1163 }
1164
1165 if (NT_SUCCESS(status)) {
1166 diskData->FailurePredictionEnabled = Enable;
1167 }
1168
1169 break;
1170 }
1171
1174 {
1175 //
1176 // We assume that the drive is already setup properly for
1177 // failure prediction
1178 //
1180 break;
1181 }
1182
1183 default:
1184 {
1186 }
1187 }
1188 return status;
1189}
@ FailurePredictionSense
Definition: classpnp.h:237
static NTSTATUS DiskDisableSmart(PFUNCTIONAL_DEVICE_EXTENSION FdoExtension)
Definition: diskwmi.c:293
_In_ ULONGLONG _In_ ULONGLONG _In_ BOOLEAN Enable
Definition: ntddpcm.h:142
FAILURE_PREDICTION_METHOD FailurePredictionCapability
Definition: disk.h:331
#define STATUS_INVALID_DEVICE_REQUEST
Definition: udferr_usr.h:138

Referenced by DiskEnableDisableFailurePredictPolling(), DiskFdoExecuteWmiMethod(), DiskIoctlEnableFailurePrediction(), and DiskWmiFunctionControl().

◆ DiskEnableDisableFailurePredictPolling()

NTSTATUS DiskEnableDisableFailurePredictPolling ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
BOOLEAN  Enable,
ULONG  PollTimeInSeconds 
)

Definition at line 1193 of file diskwmi.c.

1217{
1220 PDISK_DATA diskData = (PDISK_DATA)(commonExtension->DriverData);
1221
1222 PAGED_CODE();
1223
1224 if (Enable)
1225 {
1227 Enable);
1228 } else {
1230 }
1231
1232 if (NT_SUCCESS(status))
1233 {
1234 status = ClassSetFailurePredictionPoll(FdoExtension,
1237 PollTimeInSeconds);
1238
1239 //
1240 // Even if this failed we do not want to disable FP on the
1241 // hardware. FP is only ever disabled on the hardware by
1242 // specific command of the user.
1243 //
1244 }
1245
1246 return status;
1247}
NTSTATUS DiskEnableDisableFailurePrediction(PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, BOOLEAN Enable)
Definition: diskwmi.c:1126

Referenced by DiskFdoExecuteWmiMethod(), DiskInitFdo(), and DiskWmiFunctionControl().

◆ DiskEnableInfoExceptions()

NTSTATUS DiskEnableInfoExceptions ( _In_ PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
_In_ BOOLEAN  Enable 
)

Definition at line 979 of file diskwmi.c.

983{
984 PDISK_DATA diskData = (PDISK_DATA)(FdoExtension->CommonExtension.DriverData);
986 PMODE_PARAMETER_HEADER modeData;
987 PMODE_INFO_EXCEPTIONS pageData;
988 MODE_INFO_EXCEPTIONS changeablePageData;
989 ULONG modeDataSize;
990
991 PAGED_CODE();
992
993 modeDataSize = MODE_DATA_SIZE;
994
995 modeData = ExAllocatePoolWithTag(NonPagedPoolNxCacheAligned,
996 modeDataSize,
998
999 if (modeData == NULL) {
1000
1001 TracePrint((TRACE_LEVEL_ERROR, TRACE_FLAG_WMI, "DiskEnableInfoExceptions: Unable to allocate mode "
1002 "data buffer\n"));
1004 }
1005
1006 //
1007 // First see which data is actually changeable.
1008 //
1009 status = DiskGetModePage(FdoExtension->DeviceObject,
1011 1, // Page Control = 1 indicates we want changeable values.
1012 modeData,
1013 &modeDataSize,
1014 (PVOID*)&pageData);
1015
1016 if (!NT_SUCCESS(status) || pageData == NULL) {
1017 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "DiskEnableInfoExceptions: does NOT support SMART for device %p\n",
1018 FdoExtension->DeviceObject));
1019 FREE_POOL(modeData);
1020 return STATUS_NOT_SUPPORTED;
1021 }
1022
1023 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "DiskEnableInfoExceptions: DOES support SMART for device %p\n",
1024 FdoExtension->DeviceObject));
1025
1026 //
1027 // At the very least, the DEXCPT bit must be changeable.
1028 // If it's not, bail out now.
1029 //
1030 if (pageData->Dexcpt == 0) {
1031 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "DiskEnableInfoExceptions: does NOT support DEXCPT bit for device %p\n",
1032 FdoExtension->DeviceObject));
1033 FREE_POOL(modeData);
1034 return STATUS_NOT_SUPPORTED;
1035 }
1036
1037 //
1038 // Cache away which values are changeable.
1039 //
1040 RtlCopyMemory(&changeablePageData, pageData, sizeof(MODE_INFO_EXCEPTIONS));
1041
1042 //
1043 // Now get the current values.
1044 //
1045 status = DiskGetModePage(FdoExtension->DeviceObject,
1047 0, // Page Control = 0 indicates we want current values.
1048 modeData,
1049 &modeDataSize,
1050 (PVOID*)&pageData);
1051
1052 if (!NT_SUCCESS(status) || pageData == NULL) {
1053 //
1054 // At this point we know the device supports this mode page so
1055 // assert if something goes wrong here.
1056 //
1057 NT_ASSERT(NT_SUCCESS(status) && pageData);
1058 FREE_POOL(modeData);
1059 return STATUS_NOT_SUPPORTED;
1060 }
1061
1062 //
1063 // If the device is currently configured to not report any informational
1064 // exceptions and we cannot change the value of that field, there's
1065 // nothing to be done.
1066 //
1067 if (pageData->ReportMethod == 0 && changeablePageData.ReportMethod == 0) {
1068 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "DiskEnableInfoExceptions: MRIE field is 0 and is not changeable for device %p\n",
1069 FdoExtension->DeviceObject));
1070 FREE_POOL(modeData);
1071 return STATUS_NOT_SUPPORTED;
1072 }
1073
1074 //
1075 // If the PERF bit is changeable, set it now.
1076 //
1077 if (changeablePageData.Perf) {
1078 pageData->Perf = diskData->AllowFPPerfHit ? 0 : 1;
1079 }
1080
1081 //
1082 // If the MRIE field is changeable, set it to 4 so that informational
1083 // exceptions get reported with the "Recovered Error" sense key.
1084 //
1085 if (changeablePageData.ReportMethod) {
1086 pageData->ReportMethod = 4;
1087 }
1088
1089 //
1090 // Finally, set the DEXCPT bit appropriately to enable/disable
1091 // informational exception reporting and send the Mode Select.
1092 //
1093 pageData->Dexcpt = !Enable;
1094
1095 status = ClassModeSelect(FdoExtension->DeviceObject,
1096 (PCHAR)modeData,
1097 modeDataSize,
1098 pageData->PSBit);
1099
1100 //
1101 // Update the failure prediction state. Note that for this particular
1102 // mode FailurePredictionNone is used when it's not enabled.
1103 //
1104 if (NT_SUCCESS(status)) {
1105 if (Enable) {
1107 diskData->FailurePredictionEnabled = TRUE;
1108 } else {
1110 diskData->FailurePredictionEnabled = FALSE;
1111 }
1112 }
1113
1114 FREE_POOL(modeData);
1115
1116 return status;
1117}
#define MODE_DATA_SIZE
Definition: cdrom.h:691
#define FREE_POOL(_PoolPtr)
Definition: cdrom.h:782
NTSTATUS DiskGetModePage(_In_ PDEVICE_OBJECT Fdo, _In_ UCHAR PageMode, _In_ UCHAR PageControl, _In_ PMODE_PARAMETER_HEADER ModeData, _Inout_ PULONG ModeDataSize, _Out_ PVOID *PageData)
Definition: diskwmi.c:903
#define NULL
Definition: types.h:112
NTSTATUS NTAPI ClassModeSelect(_In_ PDEVICE_OBJECT Fdo, _In_reads_bytes_(Length) PCHAR ModeSelectBuffer, _In_ ULONG Length, _In_ BOOLEAN SavePages)
Definition: class.c:6873
#define DISK_TAG_INFO_EXCEPTION
Definition: disk.h:55
#define ExAllocatePoolWithTag(hernya, size, tag)
Definition: env_spec_w32.h:350
#define STATUS_NOT_SUPPORTED
Definition: ntstatus.h:423
#define MODE_PAGE_FAULT_REPORTING
Definition: scsi.h:218
#define TRACE_LEVEL_ERROR
Definition: storswtr.h:27
BOOLEAN AllowFPPerfHit
Definition: disk.h:332
#define RtlCopyMemory(Destination, Source, Length)
Definition: typedefs.h:263
char * PCHAR
Definition: typedefs.h:51
#define STATUS_INSUFFICIENT_RESOURCES
Definition: udferr_usr.h:158
#define NT_ASSERT
Definition: rtlfuncs.h:3310

Referenced by DiskIoctlEnableFailurePrediction().

◆ DiskEnableSmart()

static NTSTATUS DiskEnableSmart ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension)
static

Definition at line 271 of file diskwmi.c.

274{
275 UCHAR srbControl[sizeof(SRB_IO_CONTROL) + sizeof(SENDCMDINPARAMS)] = {0};
276 ULONG bufferSize = sizeof(srbControl);
277
280 SMART_CMD,
282 0,
283 0,
284 (PSRB_IO_CONTROL)srbControl,
285 &bufferSize);
286}
#define IOCTL_SCSI_MINIPORT_ENABLE_SMART
Definition: cdrw_hw.h:1461
#define ENABLE_SMART
Definition: ntdddisk.h:751

Referenced by DiskDetectFailurePrediction(), and DiskEnableDisableFailurePrediction().

◆ DiskEnableSmartAttributeAutosave()

_inline NTSTATUS DiskEnableSmartAttributeAutosave ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension)

Definition at line 315 of file diskwmi.c.

318{
319 UCHAR srbControl[sizeof(SRB_IO_CONTROL) + sizeof(SENDCMDINPARAMS)] = {0};
320 ULONG bufferSize = sizeof(srbControl);
321
324 SMART_CMD,
326 0xf1,
327 0,
328 (PSRB_IO_CONTROL)srbControl,
329 &bufferSize);
330}

◆ DiskExecuteSmartDiagnostics()

static NTSTATUS DiskExecuteSmartDiagnostics ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
UCHAR  Subcommand 
)
static

Definition at line 359 of file diskwmi.c.

363{
364 UCHAR srbControl[sizeof(SRB_IO_CONTROL) + sizeof(SENDCMDINPARAMS)] = {0};
365 ULONG bufferSize = sizeof(srbControl);
366
369 SMART_CMD,
371 0,
372 Subcommand,
373 (PSRB_IO_CONTROL)srbControl,
374 &bufferSize);
375}
#define IOCTL_SCSI_MINIPORT_EXECUTE_OFFLINE_DIAGS
Definition: cdrw_hw.h:1466
#define EXECUTE_OFFLINE_DIAGS
Definition: ntdddisk.h:748

Referenced by DiskFdoExecuteWmiMethod().

◆ DiskFdoExecuteWmiMethod()

NTSTATUS NTAPI DiskFdoExecuteWmiMethod ( IN PDEVICE_OBJECT  DeviceObject,
IN PIRP  Irp,
IN ULONG  GuidIndex,
IN ULONG  MethodId,
IN ULONG  InBufferSize,
IN ULONG  OutBufferSize,
IN PUCHAR  Buffer 
)

Definition at line 3045 of file diskwmi.c.

3088{
3089 PFUNCTIONAL_DEVICE_EXTENSION fdoExtension = DeviceObject->DeviceExtension;
3090 PCOMMON_DEVICE_EXTENSION commonExtension = DeviceObject->DeviceExtension;
3091 PDISK_DATA diskData = (PDISK_DATA)(commonExtension->DriverData);
3092 ULONG sizeNeeded = 0;
3094
3095 PAGED_CODE();
3096
3097 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DiskExecuteWmiMethod, DeviceObject %p, Irp %p, Guid Id %d, MethodId %d\n"
3098 " InBufferSize %#x, OutBufferSize %#x, Buffer %p\n",
3101
3102 switch(GuidIndex)
3103 {
3105 {
3106
3109 (diskData->FailurePredictionCapability ==
3111 (diskData->FailurePredictionCapability ==
3113
3114
3115 switch(MethodId)
3116 {
3117 //
3118 // void AllowPerformanceHit([in] boolean Allow)
3119 //
3121 {
3122 BOOLEAN allowPerfHit;
3123
3124 sizeNeeded = 0;
3125 if (InBufferSize >= sizeof(BOOLEAN))
3126 {
3128
3129 allowPerfHit = *((PBOOLEAN)Buffer);
3130 if (diskData->AllowFPPerfHit != allowPerfHit)
3131 {
3132 diskData->AllowFPPerfHit = allowPerfHit;
3133 if (diskData->FailurePredictionCapability ==
3135 {
3136 MODE_INFO_EXCEPTIONS modeInfo;
3137
3139 &modeInfo);
3140 if (NT_SUCCESS(status))
3141 {
3142 modeInfo.Perf = allowPerfHit ? 0 : 1;
3144 &modeInfo);
3145 }
3146 }
3147 else
3148 {
3150 }
3151 }
3152
3153 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "DiskFdoWmiExecuteMethod: AllowPerformanceHit %x for device %p --> %lx\n",
3154 allowPerfHit,
3155 fdoExtension->DeviceObject,
3156 status));
3157 } else {
3159 }
3160 break;
3161 }
3162
3163 //
3164 // void EnableDisableHardwareFailurePrediction([in] boolean Enable)
3165 //
3167 {
3169
3170 sizeNeeded = 0;
3171 if (InBufferSize >= sizeof(BOOLEAN))
3172 {
3174 enable = *((PBOOLEAN)Buffer);
3175 if (!enable)
3176 {
3177 //
3178 // If we are disabling we need to also disable
3179 // polling
3180 //
3182 fdoExtension,
3183 enable,
3184 0);
3185 }
3186
3188 fdoExtension,
3189 enable);
3190
3191 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "DiskFdoWmiExecuteMethod: EnableDisableHardwareFailurePrediction: %x for device %p --> %lx\n",
3192 enable,
3193 fdoExtension->DeviceObject,
3194 status));
3195 } else {
3197 }
3198 break;
3199 }
3200
3201 //
3202 // void EnableDisableFailurePredictionPolling(
3203 // [in] uint32 Period,
3204 // [in] boolean Enable)
3205 //
3207 {
3209 ULONG period;
3210
3211 sizeNeeded = 0;
3212 if (InBufferSize >= (sizeof(ULONG) + sizeof(BOOLEAN)))
3213 {
3214 period = *((PULONG)Buffer);
3215 Buffer += sizeof(ULONG);
3216 enable = *((PBOOLEAN)Buffer);
3217
3219 fdoExtension,
3220 enable,
3221 period);
3222
3223 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "DiskFdoWmiExecuteMethod: EnableDisableFailurePredictionPolling: %x %x for device %p --> %lx\n",
3224 enable,
3225 period,
3226 fdoExtension->DeviceObject,
3227 status));
3228 } else {
3230 }
3231 break;
3232 }
3233
3234 //
3235 // void GetFailurePredictionCapability([out] uint32 Capability)
3236 //
3238 {
3239 sizeNeeded = sizeof(ULONG);
3240 if (OutBufferSize >= sizeNeeded)
3241 {
3244 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "DiskFdoWmiExecuteMethod: GetFailurePredictionCapability: %x for device %p --> %lx\n",
3246 fdoExtension->DeviceObject,
3247 status));
3248 } else {
3250 }
3251 break;
3252 }
3253
3254 //
3255 // void EnableOfflineDiags([out] boolean Success);
3256 //
3257 case EnableOfflineDiags:
3258 {
3259 sizeNeeded = sizeof(BOOLEAN);
3260 if (OutBufferSize >= sizeNeeded)
3261 {
3262 if (diskData->FailurePredictionCapability ==
3264 {
3265 //
3266 // Initiate or resume offline diagnostics.
3267 // This may cause a loss of performance
3268 // to the disk, but mayincrease the amount
3269 // of disk checking.
3270 //
3271 status = DiskExecuteSmartDiagnostics(fdoExtension,
3272 0);
3273
3274 } else {
3276 }
3277
3279
3280 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "DiskFdoWmiExecuteMethod: EnableOfflineDiags for device %p --> %lx\n",
3281 fdoExtension->DeviceObject,
3282 status));
3283 } else {
3285 }
3286 break;
3287 }
3288
3289 //
3290 // void ReadLogSectors([in] uint8 LogAddress,
3291 // [in] uint8 SectorCount,
3292 // [out] uint32 Length,
3293 // [out, WmiSizeIs("Length")] uint8 LogSectors[]
3294 // );
3295 //
3296 case ReadLogSectors:
3297 {
3298 if (diskData->FailurePredictionCapability ==
3300 {
3301 if (InBufferSize >= sizeof(READ_LOG_SECTORS_IN))
3302 {
3303 PREAD_LOG_SECTORS_IN inParams;
3304 PREAD_LOG_SECTORS_OUT outParams;
3305 ULONG readSize;
3306
3307 inParams = (PREAD_LOG_SECTORS_IN)Buffer;
3308 readSize = inParams->SectorCount * SMART_LOG_SECTOR_SIZE;
3310 LogSectors) + readSize;
3311
3312 if (OutBufferSize >= sizeNeeded)
3313 {
3314 outParams = (PREAD_LOG_SECTORS_OUT)Buffer;
3315 status = DiskReadSmartLog(fdoExtension,
3316 inParams->SectorCount,
3317 inParams->LogAddress,
3318 outParams->LogSectors);
3319
3320 if (NT_SUCCESS(status))
3321 {
3322 outParams->Length = readSize;
3323 } else {
3324 //
3325 // SMART command failure is
3326 // indicated by successful
3327 // execution, but no data returned
3328 //
3329 outParams->Length = 0;
3331 }
3332 } else {
3334 }
3335
3336 } else {
3338 }
3339 } else {
3341 }
3342 break;
3343 }
3344
3345 // void WriteLogSectors([in] uint8 LogAddress,
3346 // [in] uint8 SectorCount,
3347 // [in] uint32 Length,
3348 // [in, WmiSizeIs("Length")] uint8 LogSectors[],
3349 // [out] boolean Success
3350 // );
3351 case WriteLogSectors:
3352 {
3353 if (diskData->FailurePredictionCapability ==
3355 {
3357 LogSectors))
3358 {
3359 PWRITE_LOG_SECTORS_IN inParams;
3360 PWRITE_LOG_SECTORS_OUT outParams;
3361 ULONG writeSize;
3362
3363 inParams = (PWRITE_LOG_SECTORS_IN)Buffer;
3364 writeSize = inParams->SectorCount * SMART_LOG_SECTOR_SIZE;
3366 LogSectors) +
3367 writeSize))
3368 {
3369 sizeNeeded = sizeof(WRITE_LOG_SECTORS_OUT);
3370
3371 if (OutBufferSize >= sizeNeeded)
3372 {
3373 outParams = (PWRITE_LOG_SECTORS_OUT)Buffer;
3374 status = DiskWriteSmartLog(fdoExtension,
3375 inParams->SectorCount,
3376 inParams->LogAddress,
3377 inParams->LogSectors);
3378
3379 if (NT_SUCCESS(status))
3380 {
3381 outParams->Success = TRUE;
3382 } else {
3383 outParams->Success = FALSE;
3385 }
3386 } else {
3388 }
3389 } else {
3391 }
3392 } else {
3394 }
3395 } else {
3397 }
3398 break;
3399 }
3400
3401 // void ExecuteSelfTest([in] uint8 Subcommand,
3402 // [out,
3403 // Values{"0", "1", "2"},
3404 // ValueMap{"Successful Completion",
3405 // "Captive Mode Required",
3406 // "Unsuccessful Completion"}
3407 // ]
3408 // uint32 ReturnCode);
3409 case ExecuteSelfTest:
3410 {
3411 if (diskData->FailurePredictionCapability ==
3413 {
3414 if (InBufferSize >= sizeof(EXECUTE_SELF_TEST_IN))
3415 {
3416 sizeNeeded = sizeof(EXECUTE_SELF_TEST_OUT);
3417 if (OutBufferSize >= sizeNeeded)
3418 {
3419 PEXECUTE_SELF_TEST_IN inParam;
3420 PEXECUTE_SELF_TEST_OUT outParam;
3421
3422 inParam = (PEXECUTE_SELF_TEST_IN)Buffer;
3423 outParam = (PEXECUTE_SELF_TEST_OUT)Buffer;
3424
3426 {
3427 status = DiskExecuteSmartDiagnostics(fdoExtension,
3428 inParam->Subcommand);
3429 if (NT_SUCCESS(status))
3430 {
3431 //
3432 // Return self test executed
3433 // without a problem
3434 //
3435 outParam->ReturnCode = 0;
3436 } else {
3437 //
3438 // Return Self test execution
3439 // failed status
3440 //
3441 outParam->ReturnCode = 2;
3443 }
3444 } else {
3445 //
3446 // If self test subcommand requires
3447 // captive mode then return that
3448 // status
3449 //
3450 outParam->ReturnCode = 1;
3452 }
3453
3454 } else {
3456 }
3457
3458 } else {
3460 }
3461 } else {
3463 }
3464
3465 break;
3466 }
3467
3468 default :
3469 {
3470 sizeNeeded = 0;
3472 break;
3473 }
3474 }
3475
3476 break;
3477 }
3478
3479 case DiskGeometryGuid:
3480 case SmartStatusGuid:
3481 case SmartDataGuid:
3482 case SmartEventGuid:
3485 {
3486 sizeNeeded = 0;
3488 break;
3489 }
3490
3491 default:
3492 {
3493 sizeNeeded = 0;
3495 }
3496 }
3497
3498 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DiskExecuteMethod Device %p, Irp %p returns %lx\n",
3500
3502 Irp,
3503 status,
3504 sizeNeeded,
3506
3507 return status;
3508}
Definition: bufpool.h:45
_In_ PIRP _In_ ULONG GuidIndex
Definition: classpnp.h:419
enum FAILURE_PREDICTION_METHOD * PFAILURE_PREDICTION_METHOD
SCSIPORT_API NTSTATUS NTAPI ClassWmiCompleteRequest(_In_ PDEVICE_OBJECT DeviceObject, _Inout_ PIRP Irp, _In_ NTSTATUS Status, _In_ ULONG BufferUsed, _In_ CCHAR PriorityBoost)
Definition: classwmi.c:1009
_In_ PIRP Irp
Definition: csq.h:116
#define SmartDataGuid
Definition: diskwmi.c:142
#define ScsiInfoExceptionsGuid
Definition: diskwmi.c:152
#define SmartEventGuid
Definition: diskwmi.c:150
#define SmartPerformFunction
Definition: diskwmi.c:143
NTSTATUS DiskWriteSmartLog(IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, IN UCHAR SectorCount, IN UCHAR LogAddress, IN PUCHAR Buffer)
Definition: diskwmi.c:429
#define GetFailurePredictionCapability
Definition: diskwmi.c:147
#define EnableDisableFailurePredictionPolling
Definition: diskwmi.c:146
#define EnableDisableHardwareFailurePrediction
Definition: diskwmi.c:145
#define EnableOfflineDiags
Definition: diskwmi.c:148
#define DiskGeometryGuid
Definition: diskwmi.c:140
#define SmartStatusGuid
Definition: diskwmi.c:141
static NTSTATUS DiskExecuteSmartDiagnostics(PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, UCHAR Subcommand)
Definition: diskwmi.c:359
#define SmartThresholdsGuid
Definition: diskwmi.c:151
#define AllowDisallowPerformanceHit
Definition: diskwmi.c:144
NTSTATUS DiskEnableDisableFailurePredictPolling(PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, BOOLEAN Enable, ULONG PollTimeInSeconds)
Definition: diskwmi.c:1193
NTSTATUS DiskReadSmartLog(IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, IN UCHAR SectorCount, IN UCHAR LogAddress, OUT PUCHAR Buffer)
Definition: diskwmi.c:379
NTSTATUS DiskGetInfoExceptionInformation(IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, IN PMODE_INFO_EXCEPTIONS ReturnPageData)
Definition: disk.c:2896
NTSTATUS DiskSetInfoExceptionInformation(IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, IN PMODE_INFO_EXCEPTIONS PageData)
Definition: disk.c:2985
#define DiskIsValidSmartSelfTest(Subcommand)
Definition: disk.h:619
GLboolean enable
Definition: glext.h:11120
#define SMART_LOG_SECTOR_SIZE
Definition: ntdddisk.h:734
#define STATUS_WMI_ITEMID_NOT_FOUND
Definition: ntstatus.h:778
#define STATUS_WMI_GUID_NOT_FOUND
Definition: ntstatus.h:776
#define BOOLEAN
Definition: pedump.c:73
long LONG
Definition: pedump.c:60
#define STATUS_BUFFER_TOO_SMALL
Definition: shellext.h:69
PDEVICE_OBJECT DeviceObject
Definition: classpnp.h:871
uint32_t * PULONG
Definition: typedefs.h:59
#define FIELD_OFFSET(t, f)
Definition: typedefs.h:255
unsigned char * PBOOLEAN
Definition: typedefs.h:53
#define STATUS_INVALID_PARAMETER
Definition: udferr_usr.h:135
_In_ PDEVICE_OBJECT DeviceObject
Definition: wdfdevice.h:2055
_In_ ULONG OutBufferSize
Definition: wdfwmi.h:87
_In_ ULONG InBufferSize
Definition: wdfwmi.h:106
_In_ ULONG MethodId
Definition: wdfwmi.h:142
#define ReadLogSectors
Definition: wmidata.h:3374
struct _EXECUTE_SELF_TEST_IN * PEXECUTE_SELF_TEST_IN
#define ExecuteSelfTest
Definition: wmidata.h:3407
struct _WRITE_LOG_SECTORS_OUT WRITE_LOG_SECTORS_OUT
struct _WRITE_LOG_SECTORS_IN * PWRITE_LOG_SECTORS_IN
#define WriteLogSectors
Definition: wmidata.h:3387
struct _READ_LOG_SECTORS_IN * PREAD_LOG_SECTORS_IN
struct _EXECUTE_SELF_TEST_OUT * PEXECUTE_SELF_TEST_OUT
struct _EXECUTE_SELF_TEST_OUT EXECUTE_SELF_TEST_OUT
struct _WRITE_LOG_SECTORS_OUT * PWRITE_LOG_SECTORS_OUT
struct _READ_LOG_SECTORS_OUT * PREAD_LOG_SECTORS_OUT
#define IO_NO_INCREMENT
Definition: iotypes.h:598

Referenced by DriverEntry().

◆ DiskFdoQueryWmiDataBlock()

NTSTATUS NTAPI DiskFdoQueryWmiDataBlock ( IN PDEVICE_OBJECT  DeviceObject,
IN PIRP  Irp,
IN ULONG  GuidIndex,
IN ULONG  BufferAvail,
OUT PUCHAR  Buffer 
)

Definition at line 2638 of file diskwmi.c.

2674{
2676 PFUNCTIONAL_DEVICE_EXTENSION fdoExtension = DeviceObject->DeviceExtension;
2677 PCOMMON_DEVICE_EXTENSION commonExtension = DeviceObject->DeviceExtension;
2678 PDISK_DATA diskData = (PDISK_DATA)(commonExtension->DriverData);
2679 ULONG sizeNeeded;
2680
2681 PAGED_CODE();
2682
2683 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DiskQueryWmiDataBlock, Device %p, Irp %p, GuiIndex %d\n"
2684 " BufferAvail %lx Buffer %p\n",
2687
2688 switch (GuidIndex)
2689 {
2690 case DiskGeometryGuid:
2691 {
2692 sizeNeeded = sizeof(DISK_GEOMETRY);
2693 if (BufferAvail >= sizeNeeded)
2694 {
2695 if (DeviceObject->Characteristics & FILE_REMOVABLE_MEDIA)
2696 {
2697 //
2698 // Issue ReadCapacity to update device extension
2699 // with information for current media.
2700 status = DiskReadDriveCapacity(commonExtension->PartitionZeroExtension->DeviceObject);
2701
2702 //
2703 // Note whether the drive is ready.
2704 diskData->ReadyStatus = status;
2705
2706 if (!NT_SUCCESS(status))
2707 {
2708 break;
2709 }
2710 }
2711
2712 //
2713 // Copy drive geometry information from device extension.
2715 &(fdoExtension->DiskGeometry),
2716 sizeof(DISK_GEOMETRY));
2717
2719 } else {
2721 }
2722 break;
2723 }
2724
2725 case SmartStatusGuid:
2726 {
2727 PSTORAGE_FAILURE_PREDICT_STATUS diskSmartStatus;
2728
2730
2731 sizeNeeded = sizeof(STORAGE_FAILURE_PREDICT_STATUS);
2732 if (BufferAvail >= sizeNeeded)
2733 {
2734 STORAGE_PREDICT_FAILURE checkFailure;
2735
2736 diskSmartStatus = (PSTORAGE_FAILURE_PREDICT_STATUS)Buffer;
2737
2738 status = DiskSendFailurePredictIoctl(fdoExtension,
2739 &checkFailure);
2740
2741 if (NT_SUCCESS(status))
2742 {
2743 if (diskData->FailurePredictionCapability ==
2745 {
2746 diskSmartStatus->Reason = *((PULONG)checkFailure.VendorSpecific);
2747 } else {
2748 diskSmartStatus->Reason = 0; // unknown
2749 }
2750
2751 diskSmartStatus->PredictFailure = (checkFailure.PredictFailure != 0);
2752 }
2753 } else {
2755 }
2756 break;
2757 }
2758
2759 case SmartDataGuid:
2760 {
2761 PSTORAGE_FAILURE_PREDICT_DATA diskSmartData;
2762
2765 (diskData->FailurePredictionCapability ==
2767
2768 sizeNeeded = sizeof(STORAGE_FAILURE_PREDICT_DATA);
2769 if (BufferAvail >= sizeNeeded)
2770 {
2772
2773 diskSmartData = (PSTORAGE_FAILURE_PREDICT_DATA)Buffer;
2774
2775 status = DiskSendFailurePredictIoctl(fdoExtension,
2776 checkFailure);
2777
2778 if (NT_SUCCESS(status))
2779 {
2780 diskSmartData->Length = 512;
2781 }
2782 } else {
2784 }
2785
2786 break;
2787 }
2788
2790 {
2791 PSTORAGE_FAILURE_PREDICT_THRESHOLDS diskSmartThresholds;
2792
2795
2796 sizeNeeded = sizeof(STORAGE_FAILURE_PREDICT_THRESHOLDS);
2797 if (BufferAvail >= sizeNeeded)
2798 {
2799 diskSmartThresholds = (PSTORAGE_FAILURE_PREDICT_THRESHOLDS)Buffer;
2801 diskSmartThresholds);
2802 } else {
2804 }
2805
2806 break;
2807 }
2808
2810 {
2811 sizeNeeded = 0;
2813 break;
2814 }
2815
2817 {
2818 PSTORAGE_SCSI_INFO_EXCEPTIONS infoExceptions;
2819 MODE_INFO_EXCEPTIONS modeInfo;
2820
2823
2824 sizeNeeded = sizeof(STORAGE_SCSI_INFO_EXCEPTIONS);
2825 if (BufferAvail >= sizeNeeded)
2826 {
2827 infoExceptions = (PSTORAGE_SCSI_INFO_EXCEPTIONS)Buffer;
2829 &modeInfo);
2830 if (NT_SUCCESS(status))
2831 {
2832 infoExceptions->PageSavable = modeInfo.PSBit;
2833 infoExceptions->Flags = modeInfo.Flags;
2834 infoExceptions->MRIE = modeInfo.ReportMethod;
2835 infoExceptions->Padding = 0;
2836 REVERSE_BYTES(&infoExceptions->IntervalTimer,
2837 &modeInfo.IntervalTimer);
2838 REVERSE_BYTES(&infoExceptions->ReportCount,
2839 &modeInfo.ReportCount)
2840 }
2841 } else {
2843 }
2844
2845 break;
2846 }
2847
2848 default:
2849 {
2850 sizeNeeded = 0;
2852 }
2853 }
2854 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DiskQueryWmiDataBlock Device %p, Irp %p returns %lx\n",
2856
2858 Irp,
2859 status,
2860 sizeNeeded,
2862
2863 return status;
2864}
_In_ PIRP _In_ ULONG _In_ ULONG BufferAvail
Definition: classpnp.h:420
NTSTATUS DiskReadFailurePredictThresholds(PFUNCTIONAL_DEVICE_EXTENSION FdoExtension, PSTORAGE_FAILURE_PREDICT_THRESHOLDS DiskSmartThresholds)
Definition: diskwmi.c:1417
#define DiskReadDriveCapacity(Fdo)
Definition: disk.h:818
#define FILE_REMOVABLE_MEDIA
Definition: nt_native.h:807
struct _DISK_GEOMETRY DISK_GEOMETRY
struct _STORAGE_PREDICT_FAILURE * PSTORAGE_PREDICT_FAILURE
#define REVERSE_BYTES(Destination, Source)
Definition: scsi.h:3465
struct _FUNCTIONAL_DEVICE_EXTENSION * PartitionZeroExtension
Definition: classpnp.h:599
NTSTATUS ReadyStatus
Definition: disk.h:319
DISK_GEOMETRY DiskGeometry
Definition: classpnp.h:888
UCHAR ReportCount[4]
Definition: scsi.h:3029
UCHAR IntervalTimer[4]
Definition: scsi.h:3028
UCHAR VendorSpecific[512]
Definition: ntddstor.h:501
#define RtlMoveMemory(Destination, Source, Length)
Definition: typedefs.h:264
struct _STORAGE_FAILURE_PREDICT_DATA * PSTORAGE_FAILURE_PREDICT_DATA
struct _STORAGE_FAILURE_PREDICT_STATUS * PSTORAGE_FAILURE_PREDICT_STATUS
struct _STORAGE_SCSI_INFO_EXCEPTIONS * PSTORAGE_SCSI_INFO_EXCEPTIONS
struct _STORAGE_FAILURE_PREDICT_THRESHOLDS STORAGE_FAILURE_PREDICT_THRESHOLDS
struct _STORAGE_FAILURE_PREDICT_STATUS STORAGE_FAILURE_PREDICT_STATUS
struct _STORAGE_FAILURE_PREDICT_THRESHOLDS * PSTORAGE_FAILURE_PREDICT_THRESHOLDS
struct _STORAGE_FAILURE_PREDICT_DATA STORAGE_FAILURE_PREDICT_DATA
struct _STORAGE_SCSI_INFO_EXCEPTIONS STORAGE_SCSI_INFO_EXCEPTIONS

Referenced by DriverEntry().

◆ DiskFdoQueryWmiRegInfo()

NTSTATUS NTAPI DiskFdoQueryWmiRegInfo ( IN PDEVICE_OBJECT  DeviceObject,
OUT ULONG RegFlags,
OUT PUNICODE_STRING  InstanceName 
)

Definition at line 2479 of file diskwmi.c.

2517{
2518 PCOMMON_DEVICE_EXTENSION commonExtension = DeviceObject->DeviceExtension;
2519 PDISK_DATA diskData = (PDISK_DATA)(commonExtension->DriverData);
2520
2521 PAGED_CODE();
2523
2526
2527 switch (diskData->FailurePredictionCapability)
2528 {
2530 {
2532 //
2533 // Fall Through
2534 //
2535 }
2537 {
2542
2543 break;
2544 }
2545
2547 {
2553 break;
2554 }
2555
2556
2557 default:
2558 {
2563 break;
2564 }
2565 }
2566
2567 //
2568 // Use devnode for FDOs
2570
2571 return STATUS_SUCCESS;
2572}
#define CLEAR_FLAG(Flags, Bit)
Definition: cdrom.h:1494
#define SET_FLAG(Flags, Bit)
Definition: cdrom.h:1493
_Out_ ULONG * RegFlags
Definition: classpnp.h:403
GUIDREGINFO DiskWmiFdoGuidList[]
Definition: diskwmi.c:92
_Must_inspect_result_ _Inout_ PFLT_VOLUME _In_opt_ PCUNICODE_STRING InstanceName
Definition: fltkernel.h:1163
#define UNREFERENCED_PARAMETER(P)
Definition: ntbasedef.h:317
#define WMIREG_FLAG_INSTANCE_PDO
Definition: wmistr.h:69
#define WMIREG_FLAG_REMOVE_GUID
Definition: wmistr.h:70
_Must_inspect_result_ _In_ ULONG Flags
Definition: wsk.h:170

Referenced by DiskFdoQueryWmiRegInfoEx(), and DriverEntry().

◆ DiskFdoQueryWmiRegInfoEx()

NTSTATUS NTAPI DiskFdoQueryWmiRegInfoEx ( IN PDEVICE_OBJECT  DeviceObject,
OUT ULONG RegFlags,
OUT PUNICODE_STRING  InstanceName,
OUT PUNICODE_STRING  MofName 
)

Definition at line 2577 of file diskwmi.c.

2620{
2622
2623 UNREFERENCED_PARAMETER(MofName);
2624
2626 RegFlags,
2627 InstanceName);
2628
2629 //
2630 // Leave MofName alone since disk doesn't have one
2631 //
2632 return(status);
2633}
NTSTATUS NTAPI DiskFdoQueryWmiRegInfo(IN PDEVICE_OBJECT DeviceObject, OUT ULONG *RegFlags, OUT PUNICODE_STRING InstanceName)
Definition: diskwmi.c:2479

Referenced by DriverEntry().

◆ DiskFdoSetWmiDataBlock()

NTSTATUS NTAPI DiskFdoSetWmiDataBlock ( IN PDEVICE_OBJECT  DeviceObject,
IN PIRP  Irp,
IN ULONG  GuidIndex,
IN ULONG  BufferSize,
IN PUCHAR  Buffer 
)

Definition at line 2869 of file diskwmi.c.

2904{
2906 PFUNCTIONAL_DEVICE_EXTENSION fdoExtension = DeviceObject->DeviceExtension;
2907 PCOMMON_DEVICE_EXTENSION commonExtension = DeviceObject->DeviceExtension;
2908 PDISK_DATA diskData = (PDISK_DATA)(commonExtension->DriverData);
2909
2910 PAGED_CODE();
2911
2912 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DiskSetWmiDataBlock, Device %p, Irp %p, GuiIndex %d\n"
2913 " BufferSize %#x Buffer %p\n",
2916
2918 {
2919 PSTORAGE_SCSI_INFO_EXCEPTIONS infoExceptions;
2920 MODE_INFO_EXCEPTIONS modeInfo = {0};
2921
2923 {
2924 infoExceptions = (PSTORAGE_SCSI_INFO_EXCEPTIONS)Buffer;
2925
2927 modeInfo.PageLength = sizeof(MODE_INFO_EXCEPTIONS) - 2;
2928
2929 modeInfo.PSBit = 0;
2930 modeInfo.Flags = infoExceptions->Flags;
2931
2932 modeInfo.ReportMethod = infoExceptions->MRIE;
2933
2934 REVERSE_BYTES(&modeInfo.IntervalTimer[0],
2935 &infoExceptions->IntervalTimer);
2936
2937 REVERSE_BYTES(&modeInfo.ReportCount[0],
2938 &infoExceptions->ReportCount);
2939
2940 if (modeInfo.Perf == 1)
2941 {
2942 diskData->AllowFPPerfHit = FALSE;
2943 } else {
2944 diskData->AllowFPPerfHit = TRUE;
2945 }
2946
2948 &modeInfo);
2949 } else {
2951 }
2952
2953 } else if (GuidIndex <= SmartThresholdsGuid)
2954 {
2956 } else {
2958 }
2959
2960 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DiskSetWmiDataBlock Device %p, Irp %p returns %lx\n",
2962
2964 Irp,
2965 status,
2966 0,
2968
2969 return status;
2970}
#define STATUS_WMI_READ_ONLY
Definition: ntstatus.h:818
struct _MODE_INFO_EXCEPTIONS MODE_INFO_EXCEPTIONS

Referenced by DriverEntry().

◆ DiskFdoSetWmiDataItem()

NTSTATUS NTAPI DiskFdoSetWmiDataItem ( IN PDEVICE_OBJECT  DeviceObject,
IN PIRP  Irp,
IN ULONG  GuidIndex,
IN ULONG  DataItemId,
IN ULONG  BufferSize,
IN PUCHAR  Buffer 
)

Definition at line 2975 of file diskwmi.c.

3013{
3015
3016 PAGED_CODE();
3017
3018 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DiskSetWmiDataItem, Device %p, Irp %p, GuiIndex %d, DataId %d\n"
3019 " BufferSize %#x Buffer %p\n",
3022
3024 {
3026 } else {
3028 }
3029
3030 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DiskSetWmiDataItem Device %p, Irp %p returns %lx\n",
3032
3034 Irp,
3035 status,
3036 0,
3038
3039 return status;
3040}
_In_ ULONG DataItemId
Definition: wdfwmi.h:123

Referenced by DriverEntry().

◆ DiskGetIdentifyInfo()

NTSTATUS DiskGetIdentifyInfo ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
PBOOLEAN  SupportSmart 
)

Definition at line 813 of file diskwmi.c.

817{
818 UCHAR outBuffer[sizeof(SRB_IO_CONTROL) + max( sizeof(SENDCMDINPARAMS), sizeof(SENDCMDOUTPARAMS) - 1 + IDENTIFY_BUFFER_SIZE )] = {0};
819 ULONG outBufferSize = sizeof(outBuffer);
821
822 PAGED_CODE();
823
826 &outBufferSize);
827
828 if (NT_SUCCESS(status))
829 {
830 PUSHORT identifyData = (PUSHORT)&(outBuffer[sizeof(SRB_IO_CONTROL) + sizeof(SENDCMDOUTPARAMS) - 1]);
831 USHORT commandSetSupported = identifyData[82];
832
833 *SupportSmart = ((commandSetSupported != 0xffff) &&
834 (commandSetSupported != 0) &&
835 ((commandSetSupported & 1) == 1));
836 } else {
837 *SupportSmart = FALSE;
838 }
839
840 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_IOCTL, "DiskGetIdentifyInfo: SMART %s supported for device %p, status %lx\n",
841 *SupportSmart ? "is" : "is not",
842 FdoExtension->DeviceObject,
843 status));
844
845 return status;
846}
struct _SENDCMDOUTPARAMS SENDCMDOUTPARAMS
#define DiskGetIdentifyData(FdoExtension, SrbControl, BufferSize)
Definition: diskwmi.c:254
#define IDENTIFY_BUFFER_SIZE
Definition: ntdddisk.h:732
unsigned short USHORT
Definition: pedump.c:61
PFIXED_SENSE_DATA outBuffer
Definition: scsi.h:4022
#define max(a, b)
Definition: svc.c:63
uint16_t * PUSHORT
Definition: typedefs.h:56

Referenced by DiskDetectFailurePrediction().

◆ DiskGetModePage()

NTSTATUS DiskGetModePage ( _In_ PDEVICE_OBJECT  Fdo,
_In_ UCHAR  PageMode,
_In_ UCHAR  PageControl,
_In_ PMODE_PARAMETER_HEADER  ModeData,
_Inout_ PULONG  ModeDataSize,
_Out_ PVOID PageData 
)

Definition at line 903 of file diskwmi.c.

911{
912 ULONG size = 0;
913 PVOID pageData = NULL;
914
915 PAGED_CODE();
916
917 if (ModeData == NULL ||
918 ModeDataSize == NULL ||
919 *ModeDataSize < sizeof(MODE_PARAMETER_HEADER) ||
920 PageData == NULL) {
922 }
923
924 RtlZeroMemory (ModeData, *ModeDataSize);
925
927 (PCHAR) ModeData,
928 *ModeDataSize,
929 PageMode,
931
932 if (size < sizeof(MODE_PARAMETER_HEADER)) {
933
934 //
935 // Retry the request in case of a check condition.
936 //
938 (PCHAR) ModeData,
939 *ModeDataSize,
940 PageMode,
942
943 if (size < sizeof(MODE_PARAMETER_HEADER)) {
944 TracePrint((TRACE_LEVEL_ERROR, TRACE_FLAG_WMI, "DiskGetModePage: Mode Sense for Page Mode %d with Page Control %d failed\n",
946 *ModeDataSize = 0;
948 }
949 }
950
951 //
952 // If the length is greater than length indicated by the mode data reset
953 // the data to the mode data.
954 //
955 if (size > (ULONG) (ModeData->ModeDataLength + 1)) {
956 size = ModeData->ModeDataLength + 1;
957 }
958
959 *ModeDataSize = size;
960
961 //
962 // Find the mode page
963 //
964 pageData = ClassFindModePage((PCHAR) ModeData,
965 size,
966 PageMode,
967 TRUE);
968
969 if (pageData) {
970 *PageData = pageData;
971 return STATUS_SUCCESS;
972 } else {
973 *PageData = NULL;
975 }
976}
_In_ size_t _In_ UCHAR PageMode
Definition: cdrom.h:1326
_In_ ULONG _In_ UCHAR _In_ UCHAR PageControl
Definition: cdrom.h:1319
PVOID NTAPI ClassFindModePage(_In_reads_bytes_(Length) PCHAR ModeSenseBuffer, _In_ ULONG Length, _In_ UCHAR PageMode, _In_ BOOLEAN Use6Byte)
Definition: class.c:6798
ULONG NTAPI ClassModeSenseEx(_In_ PDEVICE_OBJECT Fdo, _In_reads_bytes_(Length) PCHAR ModeSenseBuffer, _In_ ULONG Length, _In_ UCHAR PageMode, _In_ UCHAR PageControl)
Definition: class.c:6656
GLsizeiptr size
Definition: glext.h:5919
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
#define STATUS_IO_DEVICE_ERROR
Definition: udferr_usr.h:179
_Must_inspect_result_ _In_ WDFDEVICE Fdo
Definition: wdffdo.h:461

Referenced by DiskEnableInfoExceptions().

◆ DiskInfoExceptionCheck()

NTSTATUS DiskInfoExceptionCheck ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension)

Definition at line 1922 of file diskwmi.c.

1925{
1926 PUCHAR modeData;
1928 PCDB cdb;
1929 PIRP irp;
1930 PIO_STACK_LOCATION irpStack;
1932 UCHAR senseInfoBufferLength = 0;
1933 ULONG isRemoved;
1934 ULONG srbSize;
1936 PSTOR_ADDR_BTL8 storAddrBtl8 = NULL;
1937 PSRBEX_DATA_SCSI_CDB16 srbExDataCdb16 = NULL;
1938
1939 modeData = ExAllocatePoolWithTag(NonPagedPoolNxCacheAligned,
1942 if (modeData == NULL)
1943 {
1944 TracePrint((TRACE_LEVEL_WARNING, TRACE_FLAG_WMI, "DiskInfoExceptionCheck: Can't allocate mode data "
1945 "buffer\n"));
1947 }
1948
1949 if (FdoExtension->AdapterDescriptor->SrbType == SRB_TYPE_STORAGE_REQUEST_BLOCK) {
1951 } else {
1952 srbSize = SCSI_REQUEST_BLOCK_SIZE;
1953 }
1954 srb = ExAllocatePoolWithTag(NonPagedPoolNx,
1955 srbSize,
1956 DISK_TAG_SRB);
1957 if (srb == NULL)
1958 {
1959 FREE_POOL(modeData);
1960 TracePrint((TRACE_LEVEL_WARNING, TRACE_FLAG_WMI, "DiskInfoExceptionCheck: Can't allocate srb "
1961 "buffer\n"));
1963 }
1964 RtlZeroMemory(srb, srbSize);
1965
1966 //
1967 // Sense buffer is in aligned nonpaged pool.
1968 //
1969
1970 senseInfoBuffer = ExAllocatePoolWithTag(NonPagedPoolNxCacheAligned,
1972 '7CcS');
1973
1974 if (senseInfoBuffer == NULL)
1975 {
1976 FREE_POOL(srb);
1977 FREE_POOL(modeData);
1978 TracePrint((TRACE_LEVEL_WARNING, TRACE_FLAG_WMI, "DiskInfoExceptionCheck: Can't allocate request sense "
1979 "buffer\n"));
1981 }
1982
1983 senseInfoBufferLength = SENSE_BUFFER_SIZE_EX;
1984
1985 //
1986 // Build device I/O control request with METHOD_NEITHER data transfer.
1987 // We'll queue a completion routine to cleanup the MDL's and such ourself.
1988 //
1989
1991 (CCHAR) (FdoExtension->CommonExtension.LowerDeviceObject->StackSize + 1),
1992 FALSE);
1993
1994 if (irp == NULL)
1995 {
1997 FREE_POOL(srb);
1998 FREE_POOL(modeData);
1999 TracePrint((TRACE_LEVEL_WARNING, TRACE_FLAG_WMI, "DiskInfoExceptionCheck: Can't allocate Irp\n"));
2001 }
2002
2003 isRemoved = ClassAcquireRemoveLock(FdoExtension->DeviceObject, irp);
2004
2005 if (isRemoved)
2006 {
2007 ClassReleaseRemoveLock(FdoExtension->DeviceObject, irp);
2008 IoFreeIrp(irp);
2010 FREE_POOL(srb);
2011 FREE_POOL(modeData);
2012 TracePrint((TRACE_LEVEL_WARNING, TRACE_FLAG_WMI, "DiskInfoExceptionCheck: RemoveLock says isRemoved\n"));
2014 }
2015
2016 //
2017 // Get next stack location.
2018 //
2019
2022 irpStack->DeviceObject = FdoExtension->DeviceObject;
2023
2024 //
2025 // Save retry count in current Irp stack.
2026 //
2027 irpStack->Parameters.Others.Argument4 = (PVOID)MAXIMUM_RETRIES;
2028
2029 //
2030 // Save allocated sense info buffer in case the port driver overwrites it
2031 //
2032 irpStack->Parameters.Others.Argument3 = senseInfoBuffer;
2033
2034 irpStack = IoGetNextIrpStackLocation(irp);
2035
2036 //
2037 // Set up SRB for execute scsi request. Save SRB address in next stack
2038 // for the port driver.
2039 //
2040
2041 irpStack->MajorFunction = IRP_MJ_SCSI;
2042 irpStack->Parameters.Scsi.Srb = srb;
2043
2046 srb,
2047 TRUE,
2048 TRUE,
2049 TRUE);
2050
2051 irp->MdlAddress = IoAllocateMdl( modeData,
2053 FALSE,
2054 FALSE,
2055 irp );
2056 if (irp->MdlAddress == NULL)
2057 {
2058 ClassReleaseRemoveLock(FdoExtension->DeviceObject, irp);
2059 FREE_POOL(srb);
2060 FREE_POOL(modeData);
2062 IoFreeIrp( irp );
2063 TracePrint((TRACE_LEVEL_WARNING, TRACE_FLAG_WMI, "DiskINfoExceptionCheck: Can't allocate MDL\n"));
2065 }
2066
2067 MmBuildMdlForNonPagedPool(irp->MdlAddress);
2068
2069 //
2070 // Build the MODE SENSE CDB.
2071 //
2072
2073 if (FdoExtension->AdapterDescriptor->SrbType == SRB_TYPE_STORAGE_REQUEST_BLOCK) {
2074
2075 //
2076 // Set up STORAGE_REQUEST_BLOCK fields
2077 //
2078
2079 srbEx = (PSTORAGE_REQUEST_BLOCK)srb;
2081 srbEx->Function = SRB_FUNCTION_STORAGE_REQUEST_BLOCK;
2082 srbEx->Signature = SRB_SIGNATURE;
2083 srbEx->Version = STORAGE_REQUEST_BLOCK_VERSION_1;
2084 srbEx->SrbLength = srbSize;
2085 srbEx->SrbFunction = SRB_FUNCTION_EXECUTE_SCSI;
2086 srbEx->RequestPriority = IoGetIoPriorityHint(irp);
2087 srbEx->AddressOffset = sizeof(STORAGE_REQUEST_BLOCK);
2088 srbEx->NumSrbExData = 1;
2089
2090 // Set timeout value from device extension.
2091 srbEx->TimeOutValue = FdoExtension->TimeOutValue;
2092
2093 // Set the transfer length.
2094 srbEx->DataTransferLength = MODE_DATA_SIZE;
2095 srbEx->DataBuffer = modeData;
2096
2097 srbEx->SrbFlags = FdoExtension->SrbFlags;
2098
2099 SET_FLAG(srbEx->SrbFlags, SRB_FLAGS_DATA_IN);
2100
2101 //
2102 // Disable synchronous transfer for these requests.
2103 //
2105
2106 //
2107 // Don't freeze the queue on an error
2108 //
2109 SET_FLAG(srbEx->SrbFlags, SRB_FLAGS_NO_QUEUE_FREEZE);
2110
2111 srbEx->RequestAttribute = SRB_SIMPLE_TAG_REQUEST;
2112 srbEx->RequestTag = SP_UNTAGGED;
2113
2114 // Set up IRP Address.
2115 srbEx->OriginalRequest = irp;
2116
2117 //
2118 // Set up address fields
2119 //
2120
2121 storAddrBtl8 = (PSTOR_ADDR_BTL8) ((PUCHAR)srbEx + srbEx->AddressOffset);
2122 storAddrBtl8->Type = STOR_ADDRESS_TYPE_BTL8;
2123 storAddrBtl8->AddressLength = STOR_ADDR_BTL8_ADDRESS_LENGTH;
2124
2125 //
2126 // Set up SCSI SRB extended data fields
2127 //
2128
2129 srbEx->SrbExDataOffset[0] = sizeof(STORAGE_REQUEST_BLOCK) +
2130 sizeof(STOR_ADDR_BTL8);
2131 if ((srbEx->SrbExDataOffset[0] + sizeof(SRBEX_DATA_SCSI_CDB16)) <= srbEx->SrbLength) {
2132 srbExDataCdb16 = (PSRBEX_DATA_SCSI_CDB16)((PUCHAR)srbEx + srbEx->SrbExDataOffset[0]);
2133 srbExDataCdb16->Type = SrbExDataTypeScsiCdb16;
2134 srbExDataCdb16->Length = SRBEX_DATA_SCSI_CDB16_LENGTH;
2135 srbExDataCdb16->CdbLength = 6;
2136
2137 // Enable auto request sense.
2138 srbExDataCdb16->SenseInfoBufferLength = senseInfoBufferLength;
2139 srbExDataCdb16->SenseInfoBuffer = senseInfoBuffer;
2140
2141 cdb = (PCDB)srbExDataCdb16->Cdb;
2142 } else {
2143 // Should not happen
2145
2146 ClassReleaseRemoveLock(FdoExtension->DeviceObject, irp);
2147 FREE_POOL(srb);
2148 FREE_POOL(modeData);
2150 IoFreeIrp( irp );
2151 TracePrint((TRACE_LEVEL_WARNING, TRACE_FLAG_WMI, "DiskINfoExceptionCheck: Insufficient extended SRB size\n"));
2152 return STATUS_INTERNAL_ERROR;
2153 }
2154
2155 } else {
2156
2157 //
2158 // Write length to SRB.
2159 //
2161
2162 //
2163 // Set SCSI bus address.
2164 //
2165
2167
2168 //
2169 // Enable auto request sense.
2170 //
2171
2172 srb->SenseInfoBufferLength = senseInfoBufferLength;
2174
2175 //
2176 // Set timeout value from device extension.
2177 //
2178 srb->TimeOutValue = FdoExtension->TimeOutValue;
2179
2180 //
2181 // Set the transfer length.
2182 //
2184 srb->DataBuffer = modeData;
2185
2186 srb->SrbFlags = FdoExtension->SrbFlags;
2187
2189
2190 //
2191 // Disable synchronous transfer for these requests.
2192 //
2194
2195 //
2196 // Don't freeze the queue on an error
2197 //
2199
2201 srb->QueueTag = SP_UNTAGGED;
2202
2203 //
2204 // Set up IRP Address.
2205 //
2206 srb->OriginalRequest = irp;
2207
2208 srb->CdbLength = 6;
2209 cdb = (PCDB)srb->Cdb;
2210
2211 }
2212
2213 cdb->MODE_SENSE.OperationCode = SCSIOP_MODE_SENSE;
2214 cdb->MODE_SENSE.PageCode = MODE_PAGE_FAULT_REPORTING;
2215 cdb->MODE_SENSE.AllocationLength = MODE_DATA_SIZE;
2216
2217 //
2218 // Call the port driver with the request and wait for it to complete.
2219 //
2220
2222 IoCallDriver(FdoExtension->CommonExtension.LowerDeviceObject,
2223 irp);
2224
2225 return(STATUS_PENDING);
2226}
#define MAXIMUM_RETRIES
Definition: cdrom.h:124
#define SCSIOP_MODE_SENSE
Definition: cdrw_hw.h:896
union _CDB * PCDB
#define ClassAcquireRemoveLock(devobj, tag)
Definition: classpnp.h:100
#define CLASS_SRBEX_SCSI_CDB16_BUFFER_SIZE
Definition: classpnp.h:695
IO_COMPLETION_ROUTINE DiskInfoExceptionComplete
Definition: diskwmi.c:72
static const WCHAR Signature[]
Definition: parser.c:141
VOID NTAPI ClassReleaseRemoveLock(_In_ PDEVICE_OBJECT DeviceObject, _In_opt_ PIRP Tag)
Definition: lock.c:251
#define DISK_TAG_SRB
Definition: disk.h:67
#define SCSI_REQUEST_BLOCK_SIZE
Definition: srb.h:282
#define SP_UNTAGGED
Definition: srb.h:233
#define SRB_FUNCTION_EXECUTE_SCSI
Definition: srb.h:315
#define SRB_SIMPLE_TAG_REQUEST
Definition: srb.h:423
#define SRB_FLAGS_DATA_IN
Definition: srb.h:400
#define SRB_FLAGS_DISABLE_SYNCH_TRANSFER
Definition: srb.h:397
#define SRB_FLAGS_NO_QUEUE_FREEZE
Definition: srb.h:404
#define IoAllocateMdl
Definition: fxmdl.h:88
FxIrp * irp
IoMarkIrpPending(Irp)
#define IoSetCompletionRoutine(_Irp, _CompletionRoutine, _Context, _InvokeOnSuccess, _InvokeOnError, _InvokeOnCancel)
Definition: irp.cpp:490
VOID NTAPI MmBuildMdlForNonPagedPool(IN PMDL Mdl)
Definition: mdlsup.c:424
PIRP NTAPI IoAllocateIrp(IN CCHAR StackSize, IN BOOLEAN ChargeQuota)
Definition: irp.c:615
#define IoCallDriver
Definition: irp.c:1225
VOID NTAPI IoFreeIrp(IN PIRP Irp)
Definition: irp.c:1666
#define STATUS_INTERNAL_ERROR
Definition: ntstatus.h:465
#define STATUS_PENDING
Definition: ntstatus.h:82
#define STATUS_DEVICE_DOES_NOT_EXIST
Definition: ntstatus.h:428
struct STOR_ADDRESS_ALIGN _STOR_ADDR_BTL8 * PSTOR_ADDR_BTL8
#define STOR_ADDRESS_TYPE_BTL8
Definition: scsi.h:3525
struct STOR_ADDRESS_ALIGN _STOR_ADDR_BTL8 STOR_ADDR_BTL8
PFIXED_SENSE_DATA senseInfoBuffer
Definition: scsi.h:3710
#define SENSE_BUFFER_SIZE_EX
Definition: scsi.h:596
#define STOR_ADDR_BTL8_ADDRESS_LENGTH
Definition: scsi.h:3528
#define SRB_SIGNATURE
Definition: srb.h:616
#define STORAGE_REQUEST_BLOCK_VERSION_1
Definition: srb.h:617
struct SRB_ALIGN _SRBEX_DATA_SCSI_CDB16 SRBEX_DATA_SCSI_CDB16
#define SRB_TYPE_STORAGE_REQUEST_BLOCK
Definition: srb.h:664
#define SRB_FUNCTION_STORAGE_REQUEST_BLOCK
Definition: srb.h:108
* PSTORAGE_REQUEST_BLOCK
Definition: srb.h:661
@ SrbExDataTypeScsiCdb16
Definition: srb.h:459
struct SRB_ALIGN _SRBEX_DATA_SCSI_CDB16 * PSRBEX_DATA_SCSI_CDB16
STORAGE_REQUEST_BLOCK
Definition: srb.h:661
#define SRBEX_DATA_SCSI_CDB16_LENGTH
Definition: srb.h:489
#define TRACE_LEVEL_WARNING
Definition: storswtr.h:28
PDEVICE_OBJECT DeviceObject
Definition: iotypes.h:3223
struct _NAMED_PIPE_CREATE_PARAMETERS * Parameters
Definition: iotypes.h:3128
UCHAR QueueTag
Definition: srb.h:256
ULONG TimeOutValue
Definition: srb.h:262
PVOID OriginalRequest
Definition: srb.h:266
UCHAR SenseInfoBufferLength
Definition: srb.h:259
PVOID DataBuffer
Definition: srb.h:263
UCHAR QueueAction
Definition: srb.h:257
UCHAR CdbLength
Definition: srb.h:258
UCHAR Cdb[16]
Definition: srb.h:279
PVOID SenseInfoBuffer
Definition: srb.h:264
UCHAR Function
Definition: srb.h:250
ULONG DataTransferLength
Definition: srb.h:261
ULONG SrbFlags
Definition: srb.h:260
USHORT Length
Definition: srb.h:249
void * PVOID
Definition: typedefs.h:50
char CCHAR
Definition: typedefs.h:51
Definition: cdrw_hw.h:28
struct _CDB::_MODE_SENSE MODE_SENSE
__drv_aliasesMem FORCEINLINE PIO_STACK_LOCATION IoGetNextIrpStackLocation(_In_ PIRP Irp)
Definition: iofuncs.h:2695
NTKRNLVISTAAPI IO_PRIORITY_HINT NTAPI IoGetIoPriorityHint(_In_ PIRP Irp)
Definition: io.c:123
FORCEINLINE VOID IoSetNextIrpStackLocation(_Inout_ PIRP Irp)
Definition: iofuncs.h:2680
__drv_aliasesMem FORCEINLINE PIO_STACK_LOCATION IoGetCurrentIrpStackLocation(_In_ PIRP Irp)
Definition: iofuncs.h:2793
#define IRP_MJ_SCSI

Referenced by DiskDetectFailurePrediction().

◆ DiskInfoExceptionComplete()

NTSTATUS NTAPI DiskInfoExceptionComplete ( PDEVICE_OBJECT  DeviceObject,
PIRP  Irp,
PVOID  Context 
)

Definition at line 1648 of file diskwmi.c.

1653{
1654 PCOMMON_DEVICE_EXTENSION commonExtension = DeviceObject->DeviceExtension;
1655 PDISK_DATA diskData = (PDISK_DATA)(commonExtension->DriverData);
1660 BOOLEAN retry;
1661 ULONG retryInterval;
1662 ULONG srbStatus;
1663 BOOLEAN freeLockAndIrp = TRUE;
1664 PVOID originalSenseInfoBuffer = irpStack->Parameters.Others.Argument3;
1667 ULONG dataLength = 0;
1668 PVOID senseBuffer = NULL;
1669 UCHAR cdbLength8 = 0;
1670 ULONG cdbLength32 = 0;
1671 UCHAR senseBufferLength = 0;
1672
1673 srbStatus = SRB_STATUS(srb->SrbStatus);
1674
1676 srbEx = (PSTORAGE_REQUEST_BLOCK)srb;
1677 dataBuffer = srbEx->DataBuffer;
1678 dataLength = srbEx->DataTransferLength;
1679 if ((srbEx->SrbFunction == SRB_FUNCTION_EXECUTE_SCSI) &&
1680 (srbEx->NumSrbExData > 0)) {
1681 (void)GetSrbScsiData(srbEx, &cdbLength8, &cdbLength32, NULL, &senseBuffer, &senseBufferLength);
1682 }
1683 } else {
1684 dataBuffer = srb->DataBuffer;
1686 senseBuffer = srb->SenseInfoBuffer;
1687 }
1688
1689 //
1690 // Check SRB status for success of completing request.
1691 // SRB_STATUS_DATA_OVERRUN also indicates success.
1692 //
1693 if ((srbStatus != SRB_STATUS_SUCCESS) &&
1694 (srbStatus != SRB_STATUS_DATA_OVERRUN))
1695 {
1696 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_GENERAL, "DiskInfoExceptionComplete: IRP %p, SRB %p\n", Irp, srb));
1697
1699 {
1701 }
1702
1705 srb,
1706 irpStack->MajorFunction,
1707 0,
1709 ((ULONG)(ULONG_PTR)irpStack->Parameters.Others.Argument4),
1710 &status,
1711 &retryInterval);
1712
1713 //
1714 // If the status is verified required and the this request
1715 // should bypass verify required then retry the request.
1716 //
1717
1718 if (TEST_FLAG(irpStack->Flags, SL_OVERRIDE_VERIFY_VOLUME) &&
1720 {
1722 retry = TRUE;
1723 }
1724
1725 retry = retry && irpStack->Parameters.Others.Argument4;
1726
1727 irpStack->Parameters.Others.Argument4 = (PVOID)((ULONG_PTR)irpStack->Parameters.Others.Argument4 - 1);
1728
1729 if (retry)
1730 {
1731 //
1732 // Retry request.
1733 //
1734
1735 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_GENERAL, "DiskInfoExceptionComplete: Retry request %p\n", Irp));
1736
1738
1740
1741 //
1742 // Reset byte count of transfer in SRB Extension.
1743 //
1744 srbEx->DataTransferLength = Irp->MdlAddress->ByteCount;
1745
1746 //
1747 // Zero SRB statuses.
1748 //
1749
1750 srbEx->SrbStatus = 0;
1751 if ((srbEx->SrbFunction == SRB_FUNCTION_EXECUTE_SCSI) &&
1752 (srbEx->NumSrbExData > 0)) {
1753 SetSrbScsiData(srbEx, cdbLength8, cdbLength32, 0, senseBuffer, senseBufferLength);
1754 }
1755
1756 //
1757 // Set the no disconnect flag, disable synchronous data transfers and
1758 // disable tagged queuing. This fixes some errors.
1759 //
1760
1761 SET_FLAG(srbEx->SrbFlags, SRB_FLAGS_DISABLE_DISCONNECT);
1763 CLEAR_FLAG(srbEx->SrbFlags, SRB_FLAGS_QUEUE_ACTION_ENABLE);
1764
1765 srbEx->RequestAttribute = SRB_SIMPLE_TAG_REQUEST;
1766 srbEx->RequestTag = SP_UNTAGGED;
1767
1768 } else {
1769
1770 //
1771 // Reset byte count of transfer in SRB Extension.
1772 //
1773 srb->DataTransferLength = Irp->MdlAddress->ByteCount;
1774
1775 //
1776 // Zero SRB statuses.
1777 //
1778
1779 srb->SrbStatus = srb->ScsiStatus = 0;
1780
1781 //
1782 // Set the no disconnect flag, disable synchronous data transfers and
1783 // disable tagged queuing. This fixes some errors.
1784 //
1785
1789
1791 srb->QueueTag = SP_UNTAGGED;
1792 }
1793
1794 //
1795 // Set up major SCSI function.
1796 //
1797
1798 nextIrpStack->MajorFunction = IRP_MJ_SCSI;
1799
1800 //
1801 // Save SRB address in next stack for port driver.
1802 //
1803
1804 nextIrpStack->Parameters.Scsi.Srb = srb;
1805
1806
1809 srb,
1810 TRUE, TRUE, TRUE);
1811
1812 (VOID)IoCallDriver(commonExtension->LowerDeviceObject, Irp);
1813
1815 }
1816
1817 } else {
1818
1819 //
1820 // Get the results from the mode sense
1821 //
1822 PMODE_INFO_EXCEPTIONS pageData;
1823 PMODE_PARAMETER_HEADER modeData;
1824 ULONG modeDataLength;
1825
1826 modeData = dataBuffer;
1827 modeDataLength = dataLength;
1828
1829 pageData = ClassFindModePage((PCHAR)modeData,
1830 modeDataLength,
1832 TRUE);
1833 if (pageData != NULL)
1834 {
1835 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "DiskInfoExceptionComplete: %p supports SMART\n",
1836 DeviceObject));
1837
1839
1840 //
1841 // The DEXCPT bit must be 0 and the MRIE field must be valid.
1842 //
1843 if (pageData->Dexcpt == 0 &&
1844 pageData->ReportMethod >= 2 &&
1845 pageData->ReportMethod <= 6)
1846 {
1848 diskData->FailurePredictionEnabled = TRUE;
1850
1851 if (NT_SUCCESS(status))
1852 {
1853 //
1854 // Make sure we won't free the remove lock and the irp
1855 // since we need to keep these until after the work
1856 // item has completed running
1857 //
1858 freeLockAndIrp = FALSE;
1859 }
1860 } else {
1861 TracePrint((TRACE_LEVEL_WARNING, TRACE_FLAG_WMI, "DiskInfoExceptionComplete: %p is not enabled for SMART\n",
1862 DeviceObject));
1863
1864 }
1865
1866 } else {
1867 TracePrint((TRACE_LEVEL_WARNING, TRACE_FLAG_WMI, "DiskInfoExceptionComplete: %p does not supports SMART\n",
1868 DeviceObject));
1869
1870 }
1871
1872 //
1873 // Set status for successful request
1874 //
1875
1877
1878 } // end if (SRB_STATUS(srb->SrbStatus) == SRB_STATUS_SUCCESS)
1879
1880 //
1881 // Free the srb
1882 //
1883 if (senseBuffer != originalSenseInfoBuffer)
1884 {
1885 //
1886 // Free the original sense info buffer in case the port driver has overwritten it
1887 //
1888 FREE_POOL(originalSenseInfoBuffer);
1889 }
1890
1891 FREE_POOL(senseBuffer);
1893 FREE_POOL(srb);
1894
1895 if (freeLockAndIrp)
1896 {
1897 //
1898 // Set status in completing IRP.
1899 //
1900
1901 Irp->IoStatus.Status = status;
1902
1903 //
1904 // If pending has be returned for this irp then mark the current stack as
1905 // pending.
1906 //
1907
1908 if (Irp->PendingReturned) {
1910 }
1911
1913 IoFreeMdl(Irp->MdlAddress);
1914 IoFreeIrp(Irp);
1915 }
1916
1918}
#define VOID
Definition: acefi.h:82
#define TEST_FLAG(Flags, Bit)
Definition: cdrom.h:1495
NTSTATUS DiskPostReregisterRequest(PDEVICE_OBJECT DeviceObject, PIRP Irp)
Definition: diskwmi.c:1577
VOID NTAPI ClassReleaseQueue(_In_ PDEVICE_OBJECT Fdo)
Definition: class.c:11589
BOOLEAN NTAPI ClassInterpretSenseInfo(_In_ PDEVICE_OBJECT Fdo, _In_ PSCSI_REQUEST_BLOCK _Srb, _In_ UCHAR MajorFunctionCode, _In_ ULONG IoDeviceCode, _In_ ULONG RetryCount, _Out_ NTSTATUS *Status, _Out_opt_ _Deref_out_range_(0, 100) ULONG *RetryInterval)
Definition: class.c:4452
FORCEINLINE VOID SetSrbScsiData(_In_ PSTORAGE_REQUEST_BLOCK SrbEx, _In_ UCHAR CdbLength8, _In_ ULONG CdbLength32, _In_ UCHAR ScsiStatus, _In_opt_ PVOID SenseInfoBuffer, _In_ UCHAR SenseInfoBufferLength)
Definition: disk.h:1184
FORCEINLINE PCDB GetSrbScsiData(_In_ PSTORAGE_REQUEST_BLOCK SrbEx, _In_opt_ PUCHAR CdbLength8, _In_opt_ PULONG CdbLength32, _In_opt_ PUCHAR ScsiStatus, _In_opt_ PVOID *SenseInfoBuffer, _In_opt_ PUCHAR SenseInfoBufferLength)
Definition: disk.h:994
#define SRB_STATUS_DATA_OVERRUN
Definition: srb.h:357
#define SRB_FLAGS_DISABLE_DISCONNECT
Definition: srb.h:396
#define SRB_FLAGS_QUEUE_ACTION_ENABLE
Definition: srb.h:395
#define SRB_STATUS(Status)
Definition: srb.h:389
#define SRB_STATUS_QUEUE_FROZEN
Definition: srb.h:386
#define SRB_STATUS_SUCCESS
Definition: srb.h:341
#define IoFreeMdl
Definition: fxmdl.h:89
PVOID dataBuffer
ULONG dataLength
Definition: scsi.h:3751
#define STATUS_MORE_PROCESSING_REQUIRED
Definition: shellext.h:68
PDEVICE_OBJECT LowerDeviceObject
Definition: classpnp.h:598
BOOLEAN ScsiInfoExceptionsSupported
Definition: disk.h:340
UCHAR ScsiStatus
Definition: srb.h:252
UCHAR SrbStatus
Definition: srb.h:251
uint32_t ULONG_PTR
Definition: typedefs.h:65
#define STATUS_VERIFY_REQUIRED
Definition: udferr_usr.h:130
#define SL_OVERRIDE_VERIFY_VOLUME
Definition: iotypes.h:1823
#define MmGetMdlVirtualAddress(_Mdl)

◆ DiskInitializeReregistration()

NTSTATUS DiskInitializeReregistration ( VOID  )

Definition at line 1560 of file diskwmi.c.

1563{
1564 PAGED_CODE();
1565
1566 //
1567 // Initialize the spinlock used to manage the
1568 // list of disks reregistering their guids
1569 //
1571
1572 return(STATUS_SUCCESS);
1573}
KSPIN_LOCK DiskReregSpinlock
Definition: diskwmi.c:89
#define KeInitializeSpinLock(sl)
Definition: env_spec_w32.h:604

Referenced by DriverEntry().

◆ DiskPerformSmartCommand()

NTSTATUS DiskPerformSmartCommand ( IN PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
IN ULONG  SrbControlCode,
IN UCHAR  Command,
IN UCHAR  Feature,
IN UCHAR  SectorCount,
IN UCHAR  SectorNumber,
IN OUT PSRB_IO_CONTROL  SrbControl,
OUT PULONG  BufferSize 
)

Definition at line 476 of file diskwmi.c.

518{
520 PDISK_DATA diskData = (PDISK_DATA)(commonExtension->DriverData);
522 PSENDCMDINPARAMS cmdInParameters;
524 ULONG availableBufferSize;
526 PIRP irp;
527 IO_STATUS_BLOCK ioStatus = { 0 };
528 SCSI_REQUEST_BLOCK srb = {0};
529 LARGE_INTEGER startingOffset;
531 PIO_STACK_LOCATION irpStack;
534 PSTOR_ADDR_BTL8 storAddrBtl8;
535
536 PAGED_CODE();
537
538 //
539 // Point to the 'buffer' portion of the SRB_CONTROL and compute how
540 // much room we have left in the srb control. Abort if the buffer
541 // isn't at least the size of SRB_IO_CONTROL.
542 //
543
544 buffer = (PUCHAR)SrbControl + sizeof(SRB_IO_CONTROL);
545
546 cmdInParameters = (PSENDCMDINPARAMS)buffer;
547
548 if (*BufferSize >= sizeof(SRB_IO_CONTROL)) {
549 availableBufferSize = *BufferSize - sizeof(SRB_IO_CONTROL);
550 } else {
552 }
553
554#if DBG
555
556 //
557 // Ensure control codes and buffer lengths passed are correct
558 //
559 {
560 ULONG controlCode = 0;
561 ULONG lengthNeeded = sizeof(SENDCMDINPARAMS);
562
563 if (Command == SMART_CMD)
564 {
565 switch (Feature)
566 {
567 case ENABLE_SMART:
568 {
570 break;
571 }
572
573 case DISABLE_SMART:
574 {
576 break;
577 }
578
580 {
582 lengthNeeded = max( lengthNeeded, sizeof(SENDCMDOUTPARAMS) - 1 + sizeof(IDEREGS) );
583 break;
584 }
585
587 {
589 break;
590 }
591
593 {
595 break;
596 }
597
598
600 {
602 break;
603 }
604
605 case READ_ATTRIBUTES:
606 {
608 lengthNeeded = max( lengthNeeded, sizeof(SENDCMDOUTPARAMS) - 1 + READ_ATTRIBUTE_BUFFER_SIZE );
609 break;
610 }
611
612 case READ_THRESHOLDS:
613 {
615 lengthNeeded = max( lengthNeeded, sizeof(SENDCMDOUTPARAMS) - 1 + READ_THRESHOLD_BUFFER_SIZE );
616 break;
617 }
618
619 case SMART_READ_LOG:
620 {
622 lengthNeeded = max( lengthNeeded, sizeof(SENDCMDOUTPARAMS) - 1 + (SectorCount * SMART_LOG_SECTOR_SIZE) );
623 break;
624 }
625
626 case SMART_WRITE_LOG:
627 {
629 lengthNeeded = lengthNeeded - 1 + (SectorCount * SMART_LOG_SECTOR_SIZE);
630 break;
631 }
632
633 }
634
635 } else if (Command == ID_CMD) {
636
637 controlCode = IOCTL_SCSI_MINIPORT_IDENTIFY;
638 lengthNeeded = max( lengthNeeded, sizeof(SENDCMDOUTPARAMS) - 1 + IDENTIFY_BUFFER_SIZE );
639
640 } else {
641
643 }
644
645 NT_ASSERT(controlCode == SrbControlCode);
646 NT_ASSERT(availableBufferSize >= lengthNeeded);
647 }
648
649#endif
650
651 //
652 // Build SrbControl and input to SMART command
653 //
654 SrbControl->HeaderLength = sizeof(SRB_IO_CONTROL);
655 RtlMoveMemory (SrbControl->Signature, "SCSIDISK", 8);
656 SrbControl->Timeout = FdoExtension->TimeOutValue;
657 SrbControl->Length = availableBufferSize;
658 SrbControl->ControlCode = SrbControlCode;
659
660 cmdInParameters->cBufferSize = sizeof(SENDCMDINPARAMS);
661 cmdInParameters->bDriveNumber = diskData->ScsiAddress.TargetId;
662 cmdInParameters->irDriveRegs.bFeaturesReg = Feature;
663 cmdInParameters->irDriveRegs.bSectorCountReg = SectorCount;
664 cmdInParameters->irDriveRegs.bSectorNumberReg = SectorNumber;
665 cmdInParameters->irDriveRegs.bCylLowReg = SMART_CYL_LOW;
666 cmdInParameters->irDriveRegs.bCylHighReg = SMART_CYL_HI;
667 cmdInParameters->irDriveRegs.bCommandReg = Command;
668
669 //
670 // Create and send irp
671 //
673
674 startingOffset.QuadPart = (LONGLONG) 1;
675
676 length = SrbControl->HeaderLength + SrbControl->Length;
677
680 commonExtension->LowerDeviceObject,
681 SrbControl,
682 length,
683 &startingOffset,
684 &event,
685 &ioStatus);
686
687 if (irp == NULL) {
689 }
690
691 irpStack = IoGetNextIrpStackLocation(irp);
692
693 //
694 // Set major and minor codes.
695 //
696
697 irpStack->MajorFunction = IRP_MJ_SCSI;
698 irpStack->MinorFunction = 1;
699
700 //
701 // Fill in SRB fields.
702 //
703
704 if (FdoExtension->AdapterDescriptor->SrbType == SRB_TYPE_STORAGE_REQUEST_BLOCK) {
705 irpStack->Parameters.Others.Argument1 = srbEx;
706
707 //
708 // Set up STORAGE_REQUEST_BLOCK fields
709 //
710
712 srbEx->Function = SRB_FUNCTION_STORAGE_REQUEST_BLOCK;
713 srbEx->Signature = SRB_SIGNATURE;
714 srbEx->Version = STORAGE_REQUEST_BLOCK_VERSION_1;
715 srbEx->SrbLength = sizeof(srbExBuffer);
716 srbEx->SrbFunction = SRB_FUNCTION_IO_CONTROL;
717 srbEx->RequestPriority = IoGetIoPriorityHint(irp);
718 srbEx->AddressOffset = sizeof(STORAGE_REQUEST_BLOCK);
719
720 srbEx->SrbFlags = FdoExtension->SrbFlags;
721 SET_FLAG(srbEx->SrbFlags, SRB_FLAGS_DATA_IN);
722 SET_FLAG(srbEx->SrbFlags, SRB_FLAGS_NO_QUEUE_FREEZE);
723 SET_FLAG(srbEx->SrbFlags, SRB_FLAGS_NO_KEEP_AWAKE);
724
725 srbEx->RequestAttribute = SRB_SIMPLE_TAG_REQUEST;
726 srbEx->RequestTag = SP_UNTAGGED;
727
728 srbEx->OriginalRequest = irp;
729
730 //
731 // Set timeout to requested value.
732 //
733
734 srbEx->TimeOutValue = SrbControl->Timeout;
735
736 //
737 // Set the data buffer.
738 //
739
740 srbEx->DataBuffer = SrbControl;
741 srbEx->DataTransferLength = length;
742
743 //
744 // Set up address fields
745 //
746
747 storAddrBtl8 = (PSTOR_ADDR_BTL8) ((PUCHAR)srbEx + srbEx->AddressOffset);
748 storAddrBtl8->Type = STOR_ADDRESS_TYPE_BTL8;
749 storAddrBtl8->AddressLength = STOR_ADDR_BTL8_ADDRESS_LENGTH;
750 storAddrBtl8->Path = diskData->ScsiAddress.PathId;
751 storAddrBtl8->Target = diskData->ScsiAddress.TargetId;
752 storAddrBtl8->Lun = srb.Lun = diskData->ScsiAddress.Lun;
753
754 } else {
755 irpStack->Parameters.Others.Argument1 = &srb;
756
757 srb.PathId = diskData->ScsiAddress.PathId;
758 srb.TargetId = diskData->ScsiAddress.TargetId;
759 srb.Lun = diskData->ScsiAddress.Lun;
760
762 srb.Length = sizeof(SCSI_REQUEST_BLOCK);
763
764 srb.SrbFlags = FdoExtension->SrbFlags;
768
770 srb.QueueTag = SP_UNTAGGED;
771
772 srb.OriginalRequest = irp;
773
774 //
775 // Set timeout to requested value.
776 //
777
778 srb.TimeOutValue = SrbControl->Timeout;
779
780 //
781 // Set the data buffer.
782 //
783
784 srb.DataBuffer = SrbControl;
786 }
787
788 //
789 // Flush the data buffer for output. This will insure that the data is
790 // written back to memory. Since the data-in flag is the the port driver
791 // will flush the data again for input which will ensure the data is not
792 // in the cache.
793 //
794
795 KeFlushIoBuffers(irp->MdlAddress, FALSE, TRUE);
796
797 //
798 // Call port driver to handle this request.
799 //
800
801 status = IoCallDriver(commonExtension->LowerDeviceObject, irp);
802
803 if (status == STATUS_PENDING) {
805 status = ioStatus.Status;
806 }
807
808 return status;
809}
struct _SENDCMDINPARAMS SENDCMDINPARAMS
struct _SENDCMDINPARAMS * PSENDCMDINPARAMS
_In_ ULONG const _In_ FEATURE_NUMBER const Feature
Definition: cdrom.h:1077
#define IOCTL_SCSI_MINIPORT_SAVE_ATTRIBUTE_VALUES
Definition: cdrw_hw.h:1465
#define CLASS_SRBEX_NO_SRBEX_DATA_BUFFER_SIZE
Definition: classpnp.h:696
#define IOCTL_SCSI_MINIPORT_WRITE_SMART_LOG
Definition: scsi.h:1421
#define IOCTL_SCSI_MINIPORT_READ_SMART_LOG
Definition: scsi.h:1420
struct _SCSI_REQUEST_BLOCK SCSI_REQUEST_BLOCK
#define SRB_FUNCTION_IO_CONTROL
Definition: srb.h:317
#define SRB_FLAGS_NO_KEEP_AWAKE
Definition: srb.h:412
#define KeWaitForSingleObject(pEvt, foo, a, b, c)
Definition: env_spec_w32.h:478
#define KeInitializeEvent(pEvt, foo, foo2)
Definition: env_spec_w32.h:477
struct _cl_event * event
Definition: glext.h:7739
GLuint buffer
Definition: glext.h:5915
GLuint GLsizei GLsizei * length
Definition: glext.h:6040
#define KernelMode
Definition: asm.h:34
#define SMART_WRITE_LOG
Definition: ntdddisk.h:750
#define SMART_CYL_LOW
Definition: ntdddisk.h:679
#define READ_ATTRIBUTE_BUFFER_SIZE
Definition: ntdddisk.h:731
#define SAVE_ATTRIBUTE_VALUES
Definition: ntdddisk.h:747
#define SMART_READ_LOG
Definition: ntdddisk.h:749
#define READ_THRESHOLD_BUFFER_SIZE
Definition: ntdddisk.h:733
#define SMART_CYL_HI
Definition: ntdddisk.h:680
@ NotificationEvent
PIRP NTAPI IoBuildSynchronousFsdRequest(IN ULONG MajorFunction, IN PDEVICE_OBJECT DeviceObject, IN PVOID Buffer, IN ULONG Length, IN PLARGE_INTEGER StartingOffset, IN PKEVENT Event, IN PIO_STATUS_BLOCK IoStatusBlock)
Definition: irp.c:1069
ULONG SectorCount
Definition: part_xbox.c:31
#define KeFlushIoBuffers(_Mdl, _ReadOperation, _DmaOperation)
Definition: ke.h:174
Definition: shell.h:41
Definition: helper.h:8
UCHAR bCylHighReg
Definition: helper.h:13
UCHAR bSectorNumberReg
Definition: helper.h:11
UCHAR bCylLowReg
Definition: helper.h:12
UCHAR bSectorCountReg
Definition: helper.h:10
UCHAR bFeaturesReg
Definition: helper.h:9
UCHAR bCommandReg
Definition: helper.h:15
UCHAR TargetId
Definition: srb.h:254
UCHAR PathId
Definition: srb.h:253
UCHAR bDriveNumber
Definition: helper.h:33
ULONG cBufferSize
Definition: helper.h:31
IDEREGS irDriveRegs
Definition: helper.h:32
int64_t LONGLONG
Definition: typedefs.h:68
LONGLONG QuadPart
Definition: typedefs.h:114
@ Executive
Definition: ketypes.h:415

Referenced by DiskDisableSmart(), DiskDisableSmartAttributeAutosave(), DiskEnableSmart(), DiskEnableSmartAttributeAutosave(), DiskExecuteSmartDiagnostics(), DiskReadSmartLog(), and DiskWriteSmartLog().

◆ DiskPostReregisterRequest()

NTSTATUS DiskPostReregisterRequest ( PDEVICE_OBJECT  DeviceObject,
PIRP  Irp 
)

Definition at line 1577 of file diskwmi.c.

1581{
1582 PDISKREREGREQUEST reregRequest;
1583 PIO_WORKITEM workItem;
1585
1586 workItem = IoAllocateWorkItem(DeviceObject);
1587
1588 if (!workItem) {
1590 }
1591
1592 reregRequest = ExAllocatePoolWithTag(NonPagedPoolNx,
1593 sizeof(DISKREREGREQUEST),
1595 if (reregRequest != NULL)
1596 {
1597 //
1598 // add the disk that needs reregistration to the stack of disks
1599 // to reregister. If the list is transitioning from empty to
1600 // non empty then also kick off the work item so that the
1601 // reregistration worker can do the reregister.
1602 //
1603 reregRequest->DeviceObject = DeviceObject;
1604 reregRequest->Irp = Irp;
1607 &reregRequest->Next,
1609
1611 {
1612 //
1613 // There is no worker routine running, queue this one.
1614 // When the work item runs, it will process the reregistration
1615 // list.
1616 //
1617
1618 IoQueueWorkItem(workItem,
1621 workItem);
1622 } else {
1623
1624 //
1625 // There is a worker routine already running, so we
1626 // can free this unused work item.
1627 //
1628
1629 IoFreeWorkItem(workItem);
1630 }
1631
1633
1634 } else {
1635
1636 IoFreeWorkItem(workItem);
1637 TracePrint((TRACE_LEVEL_ERROR, TRACE_FLAG_GENERAL, "DiskPostReregisterRequest: could not allocate reregRequest for %p\n",
1638 DeviceObject));
1640 }
1641
1642 return(status);
1643}
#define InterlockedIncrement
Definition: armddk.h:53
SINGLE_LIST_ENTRY DiskReregHead
Definition: diskwmi.c:88
LONG DiskReregWorkItems
Definition: diskwmi.c:90
IO_WORKITEM_ROUTINE DiskReregWorker
Definition: diskwmi.c:70
#define DISK_TAG_SMART
Definition: disk.h:54
PSINGLE_LIST_ENTRY NTAPI ExInterlockedPushEntryList(IN OUT PSINGLE_LIST_ENTRY ListHead, IN OUT PSINGLE_LIST_ENTRY ListEntry, IN OUT PKSPIN_LOCK Lock)
Definition: interlocked.c:227
VOID NTAPI IoQueueWorkItem(IN PIO_WORKITEM IoWorkItem, IN PIO_WORKITEM_ROUTINE WorkerRoutine, IN WORK_QUEUE_TYPE QueueType, IN PVOID Context)
Definition: iowork.c:40
VOID NTAPI IoFreeWorkItem(IN PIO_WORKITEM IoWorkItem)
Definition: iowork.c:64
PIO_WORKITEM NTAPI IoAllocateWorkItem(IN PDEVICE_OBJECT DeviceObject)
Definition: iowork.c:75
SINGLE_LIST_ENTRY Next
Definition: disk.h:430
PDEVICE_OBJECT DeviceObject
Definition: disk.h:431
@ DelayedWorkQueue
Definition: extypes.h:190

Referenced by DiskInfoExceptionComplete().

◆ DiskReadFailurePredictData()

NTSTATUS DiskReadFailurePredictData ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
PSTORAGE_FAILURE_PREDICT_DATA  DiskSmartData 
)

Definition at line 1327 of file diskwmi.c.

1349{
1351 PDISK_DATA diskData = (PDISK_DATA)(commonExtension->DriverData);
1353
1354 PAGED_CODE();
1355
1356 switch(diskData->FailurePredictionCapability)
1357 {
1359 {
1361 ULONG outBufferSize;
1362 PSENDCMDOUTPARAMS cmdOutParameters;
1363
1364 outBufferSize = sizeof(SRB_IO_CONTROL) + max( sizeof(SENDCMDINPARAMS), sizeof(SENDCMDOUTPARAMS) - 1 + READ_ATTRIBUTE_BUFFER_SIZE );
1365
1366 outBuffer = ExAllocatePoolWithTag(NonPagedPoolNx,
1367 outBufferSize,
1369
1370 if (outBuffer != NULL)
1371 {
1374 &outBufferSize);
1375
1376 if (NT_SUCCESS(status))
1377 {
1378 cmdOutParameters = (PSENDCMDOUTPARAMS)(outBuffer +
1379 sizeof(SRB_IO_CONTROL));
1380
1381 DiskSmartData->Length = READ_ATTRIBUTE_BUFFER_SIZE;
1382 RtlCopyMemory(DiskSmartData->VendorSpecific,
1383 cmdOutParameters->bBuffer,
1384 min(READ_ATTRIBUTE_BUFFER_SIZE, sizeof(DiskSmartData->VendorSpecific)));
1385 }
1387 } else {
1389 }
1390
1391 break;
1392 }
1393
1395 {
1396 DiskSmartData->Length = sizeof(ULONG);
1397 *((PULONG)DiskSmartData->VendorSpecific) = FdoExtension->FailureReason;
1398
1400 break;
1401 }
1402
1405 default:
1406 {
1408 break;
1409 }
1410 }
1411
1412 return status;
1413}
struct _SENDCMDOUTPARAMS * PSENDCMDOUTPARAMS
#define DiskReadSmartData(FdoExtension, SrbControl, BufferSize)
Definition: diskwmi.c:200
#define min(a, b)
Definition: monoChain.cc:55
UCHAR bBuffer[1]
Definition: helper.h:27

Referenced by DiskIoctlPredictFailure().

◆ DiskReadFailurePredictStatus()

NTSTATUS DiskReadFailurePredictStatus ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
PSTORAGE_FAILURE_PREDICT_STATUS  DiskSmartStatus 
)

Definition at line 1251 of file diskwmi.c.

1272{
1274 PDISK_DATA diskData = (PDISK_DATA)(commonExtension->DriverData);
1276
1277 PAGED_CODE();
1278
1279 DiskSmartStatus->PredictFailure = FALSE;
1280
1281 switch(diskData->FailurePredictionCapability)
1282 {
1284 {
1285 UCHAR outBuffer[sizeof(SRB_IO_CONTROL) + max( sizeof(SENDCMDINPARAMS), sizeof(SENDCMDOUTPARAMS) - 1 + sizeof(IDEREGS) )] = {0};
1286 ULONG outBufferSize = sizeof(outBuffer);
1287 PSENDCMDOUTPARAMS cmdOutParameters;
1288
1291 &outBufferSize);
1292
1293 if (NT_SUCCESS(status))
1294 {
1295 cmdOutParameters = (PSENDCMDOUTPARAMS)(outBuffer +
1296 sizeof(SRB_IO_CONTROL));
1297
1298 DiskSmartStatus->Reason = 0; // Unknown;
1299 DiskSmartStatus->PredictFailure = ((cmdOutParameters->bBuffer[3] == 0xf4) &&
1300 (cmdOutParameters->bBuffer[4] == 0x2c));
1301 }
1302 break;
1303 }
1304
1306 {
1307 DiskSmartStatus->Reason = FdoExtension->FailureReason;
1308 DiskSmartStatus->PredictFailure = FdoExtension->FailurePredicted;
1310 break;
1311 }
1312
1315 default:
1316 {
1318 break;
1319 }
1320 }
1321
1322 return status;
1323}
#define DiskReadSmartStatus(FdoExtension, SrbControl, BufferSize)
Definition: diskwmi.c:236

Referenced by DiskDetectFailurePrediction(), and DiskIoctlPredictFailure().

◆ DiskReadFailurePredictThresholds()

NTSTATUS DiskReadFailurePredictThresholds ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
PSTORAGE_FAILURE_PREDICT_THRESHOLDS  DiskSmartThresholds 
)

Definition at line 1417 of file diskwmi.c.

1439{
1441 PDISK_DATA diskData = (PDISK_DATA)(commonExtension->DriverData);
1443
1444 PAGED_CODE();
1445
1446 switch(diskData->FailurePredictionCapability)
1447 {
1449 {
1451 PSENDCMDOUTPARAMS cmdOutParameters;
1452 ULONG outBufferSize;
1453
1454 outBufferSize = sizeof(SRB_IO_CONTROL) + max( sizeof(SENDCMDINPARAMS), sizeof(SENDCMDOUTPARAMS) - 1 + READ_THRESHOLD_BUFFER_SIZE );
1455
1456 outBuffer = ExAllocatePoolWithTag(NonPagedPoolNx,
1457 outBufferSize,
1459
1460 if (outBuffer != NULL)
1461 {
1464 &outBufferSize);
1465
1466 if (NT_SUCCESS(status))
1467 {
1468 cmdOutParameters = (PSENDCMDOUTPARAMS)(outBuffer +
1469 sizeof(SRB_IO_CONTROL));
1470
1471 RtlCopyMemory(DiskSmartThresholds->VendorSpecific,
1472 cmdOutParameters->bBuffer,
1473 min(READ_THRESHOLD_BUFFER_SIZE, sizeof(DiskSmartThresholds->VendorSpecific)));
1474 }
1476 } else {
1478 }
1479
1480 break;
1481 }
1482
1486 default:
1487 {
1489 break;
1490 }
1491 }
1492
1493 return status;
1494}
#define DiskReadSmartThresholds(FdoExtension, SrbControl, BufferSize)
Definition: diskwmi.c:218

Referenced by DiskFdoQueryWmiDataBlock().

◆ DiskReadSmartLog()

NTSTATUS DiskReadSmartLog ( IN PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
IN UCHAR  SectorCount,
IN UCHAR  LogAddress,
OUT PUCHAR  Buffer 
)

Definition at line 379 of file diskwmi.c.

385{
386 PSRB_IO_CONTROL srbControl;
388 PSENDCMDOUTPARAMS sendCmdOutParams;
389 ULONG logSize, bufferSize;
390
391 PAGED_CODE();
392
394 bufferSize = sizeof(SRB_IO_CONTROL) + max( sizeof(SENDCMDINPARAMS), sizeof(SENDCMDOUTPARAMS) - 1 + logSize );
395
396 srbControl = ExAllocatePoolWithTag(NonPagedPoolNx,
399
400 if (srbControl != NULL)
401 {
404 SMART_CMD,
407 LogAddress,
408 srbControl,
409 &bufferSize);
410
411 if (NT_SUCCESS(status))
412 {
413 sendCmdOutParams = (PSENDCMDOUTPARAMS)((PUCHAR)srbControl +
414 sizeof(SRB_IO_CONTROL));
416 &sendCmdOutParams->bBuffer[0],
417 logSize);
418 }
419
420 FREE_POOL(srbControl);
421 } else {
423 }
424 return(status);
425}

Referenced by DiskFdoExecuteWmiMethod().

◆ DiskReregWorker()

VOID NTAPI DiskReregWorker ( IN PDEVICE_OBJECT  DevObject,
IN PVOID  Context 
)

Definition at line 1499 of file diskwmi.c.

1503{
1504 PDISKREREGREQUEST reregRequest;
1507 PIRP irp;
1508
1509 PAGED_CODE();
1510 UNREFERENCED_PARAMETER(DevObject);
1511
1514
1515 do
1516 {
1520
1521 if (reregRequest != NULL)
1522 {
1523 deviceObject = reregRequest->DeviceObject;
1524 irp = reregRequest->Irp;
1525
1528
1529 //
1530 // Release remove lock and free irp, now that we are done
1531 // processing this
1532 //
1534
1535 IoFreeMdl(irp->MdlAddress);
1536 IoFreeIrp(irp);
1537
1538 FREE_POOL(reregRequest);
1539
1540 } else {
1541
1542 NT_ASSERTMSG("Disk Re-registration request list should not be empty", FALSE);
1543
1545 }
1546
1547 if (!NT_SUCCESS(status))
1548 {
1549 TracePrint((TRACE_LEVEL_ERROR, TRACE_FLAG_GENERAL, "DiskReregWorker: Reregistration failed %x\n",
1550 status));
1551 }
1552
1554
1556}
#define InterlockedDecrement
Definition: armddk.h:52
struct DISKREREGREQUEST * PDISKREREGREQUEST
MxDeviceObject deviceObject
PSINGLE_LIST_ENTRY NTAPI ExInterlockedPopEntryList(IN OUT PSINGLE_LIST_ENTRY ListHead, IN OUT PKSPIN_LOCK Lock)
Definition: interlocked.c:201
#define _Analysis_assume_(expr)
Definition: ms_sal.h:2901
NTSTATUS NTAPI IoWMIRegistrationControl(IN PDEVICE_OBJECT DeviceObject, IN ULONG Action)
Definition: wmi.c:68
#define WMIREG_ACTION_UPDATE_GUIDS
#define NT_ASSERTMSG
Definition: rtlfuncs.h:3311

◆ DiskSendFailurePredictIoctl()

NTSTATUS DiskSendFailurePredictIoctl ( PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
PSTORAGE_PREDICT_FAILURE  checkFailure 
)

Definition at line 854 of file diskwmi.c.

858{
861 IO_STATUS_BLOCK ioStatus = { 0 };
862 PIRP irp;
864
865 PAGED_CODE();
866
868
870
874 NULL,
875 0,
876 checkFailure,
878 FALSE,
879 &event,
880 &ioStatus);
881
882 if (irp != NULL)
883 {
885 if (status == STATUS_PENDING)
886 {
888 status = ioStatus.Status;
889 }
890
891 } else {
893 }
894
896
897 return status;
898}
#define IOCTL_STORAGE_PREDICT_FAILURE
Definition: ntddstor.h:146
@ SynchronizationEvent
PDEVICE_OBJECT NTAPI IoGetAttachedDeviceReference(PDEVICE_OBJECT DeviceObject)
Definition: device.c:1406
PIRP NTAPI IoBuildDeviceIoControlRequest(IN ULONG IoControlCode, IN PDEVICE_OBJECT DeviceObject, IN PVOID InputBuffer, IN ULONG InputBufferLength, IN PVOID OutputBuffer, IN ULONG OutputBufferLength, IN BOOLEAN InternalDeviceIoControl, IN PKEVENT Event, IN PIO_STATUS_BLOCK IoStatusBlock)
Definition: irp.c:881
#define ObDereferenceObject
Definition: obfuncs.h:203

Referenced by DiskDetectFailurePrediction(), and DiskFdoQueryWmiDataBlock().

◆ DiskWmiFunctionControl()

NTSTATUS NTAPI DiskWmiFunctionControl ( IN PDEVICE_OBJECT  DeviceObject,
IN PIRP  Irp,
IN ULONG  GuidIndex,
IN CLASSENABLEDISABLEFUNCTION  Function,
IN BOOLEAN  Enable 
)

Definition at line 2366 of file diskwmi.c.

2412{
2414 PFUNCTIONAL_DEVICE_EXTENSION fdoExtension = DeviceObject->DeviceExtension;
2415
2416 PAGED_CODE();
2417
2419 {
2420 if ((GuidIndex == SmartStatusGuid) ||
2421 (GuidIndex == SmartDataGuid) ||
2424 {
2426 TRUE);
2427 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DeviceObject %p, Irp %p Enable -> %lx\n",
2429 Irp,
2430 status));
2431
2432 } else {
2433 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DeviceObject %p, Irp %p, GuidIndex %d %s for Collection\n",
2435 GuidIndex,
2436 Enable ? "Enabled" : "Disabled"));
2437 }
2438 } else if (Function == EventGeneration) {
2439 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DeviceObject %p, Irp %p, GuidIndex %d %s for Event Generation\n",
2441 GuidIndex,
2442 Enable ? "Enabled" : "Disabled"));
2443
2444
2445 if ((GuidIndex == SmartEventGuid) && Enable)
2446 {
2448 Enable,
2449 0);
2450 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DeviceObject %p, Irp %p %s -> %lx\n",
2452 Irp,
2453 Enable ? "DiskEnableSmartPolling" : "DiskDisableSmartPolling",
2454 status));
2455 }
2456
2457#if DBG
2458 } else {
2459 TracePrint((TRACE_LEVEL_INFORMATION, TRACE_FLAG_WMI, "Disk: DeviceObject %p, Irp %p, GuidIndex %d %s for function %d\n",
2461 GuidIndex,
2462 Enable ? "Enabled" : "Disabled",
2463 Function));
2464#endif
2465 }
2466
2468 Irp,
2469 status,
2470 0,
2472 return status;
2473}
_In_ CDROM_SCAN_FOR_SPECIAL_INFO _In_ PCDROM_SCAN_FOR_SPECIAL_HANDLER Function
Definition: cdrom.h:1156
@ DataBlockCollection
Definition: classpnp.h:230
@ EventGeneration
Definition: classpnp.h:229

Referenced by DriverEntry().

◆ DiskWriteSmartLog()

NTSTATUS DiskWriteSmartLog ( IN PFUNCTIONAL_DEVICE_EXTENSION  FdoExtension,
IN UCHAR  SectorCount,
IN UCHAR  LogAddress,
IN PUCHAR  Buffer 
)

Definition at line 429 of file diskwmi.c.

435{
436 PSRB_IO_CONTROL srbControl;
438 PSENDCMDINPARAMS sendCmdInParams;
439 ULONG logSize, bufferSize;
440
441 PAGED_CODE();
442
444 bufferSize = sizeof(SRB_IO_CONTROL) + sizeof(SENDCMDINPARAMS) - 1 +
445 logSize;
446
447 srbControl = ExAllocatePoolWithTag(NonPagedPoolNx,
450
451 if (srbControl != NULL)
452 {
453 sendCmdInParams = (PSENDCMDINPARAMS)((PUCHAR)srbControl +
454 sizeof(SRB_IO_CONTROL));
455 RtlCopyMemory(&sendCmdInParams->bBuffer[0],
456 Buffer,
457 logSize);
460 SMART_CMD,
463 LogAddress,
464 srbControl,
465 &bufferSize);
466
467 FREE_POOL(srbControl);
468 } else {
470 }
471 return(status);
472}
UCHAR bBuffer[1]
Definition: helper.h:36

Referenced by DiskFdoExecuteWmiMethod().

Variable Documentation

◆ DiskInfoExceptionComplete

IO_COMPLETION_ROUTINE DiskInfoExceptionComplete

Definition at line 72 of file diskwmi.c.

Referenced by DiskInfoExceptionCheck(), and DiskInfoExceptionComplete().

◆ DiskPredictFailureEventGuid

GUID DiskPredictFailureEventGuid = WMI_STORAGE_PREDICT_FAILURE_EVENT_GUID

Definition at line 138 of file diskwmi.c.

◆ DiskReregHead

SINGLE_LIST_ENTRY DiskReregHead

Definition at line 88 of file diskwmi.c.

Referenced by DiskPostReregisterRequest(), and DiskReregWorker().

◆ DiskReregSpinlock

KSPIN_LOCK DiskReregSpinlock

◆ DiskReregWorker

IO_WORKITEM_ROUTINE DiskReregWorker

Definition at line 70 of file diskwmi.c.

Referenced by DiskPostReregisterRequest().

◆ DiskReregWorkItems

LONG DiskReregWorkItems

Definition at line 90 of file diskwmi.c.

Referenced by DiskPostReregisterRequest(), and DiskReregWorker().

◆ DiskWmiFdoGuidList

GUIDREGINFO DiskWmiFdoGuidList[]

Definition at line 92 of file diskwmi.c.

Referenced by DiskFdoQueryWmiRegInfo(), and DriverEntry().