diff --git a/reactos/drivers/bus/acpi/cmbatt/cmexec.c b/reactos/drivers/bus/acpi/cmbatt/cmexec.c index a41865c5e4c..7fb4ea591bf 100644 --- a/reactos/drivers/bus/acpi/cmbatt/cmexec.c +++ b/reactos/drivers/bus/acpi/cmbatt/cmexec.c @@ -9,25 +9,73 @@ /* INCLUDES *******************************************************************/ #include "cmbatt.h" +#include "ntstatus.h" /* FUNCTIONS ******************************************************************/ NTSTATUS NTAPI -GetDwordElement(PACPI_METHOD_ARGUMENT Argument, - PULONG Value) +GetDwordElement(IN PACPI_METHOD_ARGUMENT Argument, + OUT PULONG Value) { - UNIMPLEMENTED; - return STATUS_NOT_IMPLEMENTED; + NTSTATUS Status; + + /* Must have an integer */ + if (Argument->Type != ACPI_METHOD_ARGUMENT_INTEGER) + { + /* Not an integer, fail */ + Status = STATUS_ACPI_INVALID_DATA; + if (CmBattDebug & 0x4C) + DbgPrint("GetDwordElement: Object contained wrong data type - %d\n", + Argument->Type); + } + else + { + /* Read the integer value */ + *Value = Argument->Argument; + Status = STATUS_SUCCESS; + } + + /* Return status */ + return Status; } NTSTATUS NTAPI -GetStringElement(PACPI_METHOD_ARGUMENT Argument, - PCHAR Value) +GetStringElement(IN PACPI_METHOD_ARGUMENT Argument, + OUT PCHAR Value) { - UNIMPLEMENTED; - return STATUS_NOT_IMPLEMENTED; + NTSTATUS Status; + + /* Must have a string of buffer */ + if ((Argument->Type == ACPI_METHOD_ARGUMENT_STRING) || + (Argument->Type == ACPI_METHOD_ARGUMENT_BUFFER)) + { + /* String must be less than 256 characters */ + if (Argument->DataLength < 256) + { + /* Copy the buffer */ + RtlCopyMemory(Value, Argument->Data, Argument->DataLength); + Status = STATUS_SUCCESS; + } + else + { + /* The buffer is too small (the string is too large) */ + Status = STATUS_BUFFER_TOO_SMALL; + if (CmBattDebug & 0x4C) + DbgPrint("GetStringElement: return buffer not big enough - %d\n", Argument->DataLength); + } + } + else + { + /* Not valid string data */ + Status = STATUS_ACPI_INVALID_DATA; + if (CmBattDebug & 0x4C) + DbgPrint("GetStringElement: Object contained wrong data type - %d\n", Argument->Type); + } + + /* Return the status */ + return Status; } NTSTATUS @@ -86,15 +134,72 @@ CmBattSetTripPpoint(PCMBATT_DEVICE_EXTENSION DeviceExtension, NTSTATUS NTAPI -CmBattSendDownStreamIrp(PDEVICE_OBJECT DeviceObject, - ULONG IoControlCode, - PVOID InputBuffer, - ULONG InputBufferLength, - PACPI_EVAL_OUTPUT_BUFFER OutputBuffer, - ULONG OutputBufferLength) +CmBattSendDownStreamIrp(IN PDEVICE_OBJECT DeviceObject, + IN ULONG IoControlCode, + IN PVOID InputBuffer, + IN ULONG InputBufferLength, + IN PACPI_EVAL_OUTPUT_BUFFER OutputBuffer, + IN ULONG OutputBufferLength) { - UNIMPLEMENTED; - return STATUS_NOT_IMPLEMENTED; + PIRP Irp; + NTSTATUS Status; + KEVENT Event; + IO_STATUS_BLOCK IoStatusBlock; + PAGED_CODE(); + + /* Initialize our wait event */ + KeInitializeEvent(&Event, SynchronizationEvent, 0); + + /* Allocate the IRP */ + Irp = IoBuildDeviceIoControlRequest(IoControlCode, + DeviceObject, + InputBuffer, + InputBufferLength, + OutputBuffer, + OutputBufferLength, + 0, + &Event, + &IoStatusBlock); + if (!Irp) + { + /* No IRP, fail */ + if (CmBattDebug & 0x4C) + DbgPrint("CmBattSendDownStreamIrp: Failed to allocate Irp\n"); + return STATUS_INSUFFICIENT_RESOURCES; + } + + /* Call ACPI */ + if (CmBattDebug & 0x40) + DbgPrint("CmBattSendDownStreamIrp: Irp %x [Tid] %x\n", Irp, KeGetCurrentThread()); + Status = IoCallDriver(DeviceObject, Irp); + if (Status == STATUS_PENDING) + { + /* Wait for completion */ + KeWaitForSingleObject(&Event, + Executive, + KernelMode, + FALSE, + NULL); + Status = Irp->IoStatus.Status; + } + + /* Check if caller wanted output */ + if (OutputBuffer) + { + /* Make sure it's valid ACPI output buffer */ + if ((OutputBuffer->Signature != ACPI_EVAL_OUTPUT_BUFFER_SIGNATURE) || + !(OutputBuffer->Count)) + { + /* It isn't, so set failure code */ + Status = STATUS_ACPI_INVALID_DATA; + } + } + + /* Return status */ + if (CmBattDebug & 0x40) + DbgPrint("CmBattSendDownStreamIrp: Irp %x completed %x! [Tid] %x\n", + Irp, Status, KeGetCurrentThread()); + return Status; } /* EOF */