Author: fireball
Date: Fri Jun 26 13:39:00 2009
New Revision: 41620
URL:
http://svn.reactos.org/svn/reactos?rev=41620&view=rev
Log:
- Implement NtSetThreadExecutionState (in place of what has been committed in r41599 and
reverted in 41619).
Modified:
trunk/reactos/ntoskrnl/po/power.c
Modified: trunk/reactos/ntoskrnl/po/power.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/po/power.c?rev=41…
==============================================================================
--- trunk/reactos/ntoskrnl/po/power.c [iso-8859-1] (original)
+++ trunk/reactos/ntoskrnl/po/power.c [iso-8859-1] Fri Jun 26 13:39:00 2009
@@ -588,6 +588,54 @@
NtSetThreadExecutionState(IN EXECUTION_STATE esFlags,
OUT EXECUTION_STATE *PreviousFlags)
{
- UNIMPLEMENTED;
- return STATUS_NOT_IMPLEMENTED;
-}
+ PKTHREAD Thread = KeGetCurrentThread();
+ KPROCESSOR_MODE PreviousMode = KeGetPreviousMode();
+ EXECUTION_STATE PreviousState;
+ PAGED_CODE();
+
+ /* Validate flags */
+ if (esFlags & ~(ES_CONTINUOUS | ES_USER_PRESENT))
+ {
+ /* Fail the request */
+ return STATUS_INVALID_PARAMETER;
+ }
+
+ /* Check for user parameters */
+ if (PreviousMode != KernelMode)
+ {
+ /* Protect the probes */
+ _SEH2_TRY
+ {
+ /* Check if the pointer is valid */
+ ProbeForWriteUlong(PreviousFlags);
+ }
+ _SEH2_EXCEPT(ExSystemExceptionFilter())
+ {
+ /* It isn't -- fail */
+ _SEH2_YIELD(return _SEH2_GetExceptionCode());
+ }
+ _SEH2_END;
+ }
+
+ /* Save the previous state, always masking in the continous flag */
+ PreviousState = Thread->PowerState | ES_CONTINUOUS;
+
+ /* Check if we need to update the power state */
+ if (esFlags & ES_CONTINUOUS) Thread->PowerState = esFlags;
+
+ /* Protect the write back to user mode */
+ _SEH2_TRY
+ {
+ /* Return the previous flags */
+ *PreviousFlags = PreviousState;
+ }
+ _SEH2_EXCEPT(ExSystemExceptionFilter())
+ {
+ /* Something's wrong, fail */
+ _SEH2_YIELD(return _SEH2_GetExceptionCode());
+ }
+ _SEH2_END;
+
+ /* All is good */
+ return STATUS_SUCCESS;
+}