Disabling ACPI C States from a Windows Driver?

I need to disable C states from a Windows driver. I found a way to do it from an application.

http://stackoverflow.com/questions/9721218/trying-to-disable-processor-idle-states-c-states-on-windows-pc

The problem is those APIs are for Windows apps only. I found a way to modify power schemes in a driver using an inf entry, but I don’t see how to set ACPI C states.

https://msdn.microsoft.com/en-us/windows/hardware/drivers/install/inf-addpowersetting-directive

Does anyone know if there is a way to do this?

Thanks!

What makes you think you need to modify C states from a driver?

What hardware does this driver load for?

It’s a COM port driver and it can’t use high baud rates (115K) if C states are on. Since I saw there is a way to turn them on and off I thought it might be a solution. The driver is doing buffered reads and writes and is based off of the Window’s sample COM port driver code. I doubt that it could be optimized enough, if at all, to solve this issue, but I could be wrong.

On Jan 11, 2017, at 12:58 PM, xxxxx@gmail.com wrote:

It’s a COM port driver and it can’t use high baud rates (115K) if C states are on. Since I saw there is a way to turn them on and off I thought it might be a solution. The driver is doing buffered reads and writes and is based off of the Window’s sample COM port driver code. I doubt that it could be optimized enough, if at all, to solve this issue, but I could be wrong.

You are obviously wrong. That’s practically a snail’s pace. The processor can execute 30,000 instructions between each BIT at that rate. USB 2 runs 4,000 times faster than that, and the system obviously handles it without modifying the power architecture.

You’re doing something wrong in your driver. What leads you to think you can’t handle it? Are you dropping bytes? What do you mean by “buffered reads and writes” in this context? Are you using an interrupt? Or are you polling and delaying?

Tim Roberts, xxxxx@probo.com
Providenza & Boekelheide, Inc.

Define ?can?t use?. Unless you have a design issue, processor c states should be irrelevant to you; especially at such low bandwidth

Sent from Mailhttps: for Windows 10

From: xxxxx@gmail.commailto:xxxxx
Sent: January 11, 2017 3:59 PM
To: Windows System Software Devs Interest Listmailto:xxxxx
Subject: RE:[ntdev] Disabling ACPI C States from a Windows Driver?

It’s a COM port driver and it can’t use high baud rates (115K) if C states are on. Since I saw there is a way to turn them on and off I thought it might be a solution. The driver is doing buffered reads and writes and is based off of the Window’s sample COM port driver code. I doubt that it could be optimized enough, if at all, to solve this issue, but I could be wrong.


NTDEV is sponsored by OSR

Visit the list online at: http:

MONTHLY seminars on crash dump analysis, WDF, Windows internals and software drivers!
Details at http:

To unsubscribe, visit the List Server section of OSR Online at http:</http:></http:></http:></mailto:xxxxx></mailto:xxxxx></https:>

Thank you for the replies! Yes, the driver is interrupt driven, not polled. And when I say buffered, it reads and writes blocks of characters at a time, not just one character at a time. As for what is failing exactly, I am still waiting for the customer to provide that information. Their initial request was to disable C states in the driver due to failing at high baud rates, and that is what I was looking into.

Sounds like you have some root cause analysis to do. I suspect there is a misconception between C/S/D states. It’s quite possible that they have an issue with your device when you transition through sleep states.

I would suggest you debug your driver while using pwrtest to help you go through all the combinations of sleep transitions:
https://msdn.microsoft.com/en-us/windows/hardware/drivers/devtest/pwrtest

My best guess is that you aren’t saving/restoring device state properly.

Depending on your BIOS implementation there may also be an option to disable low power states, but fixing the driver is the right approach.

Shane Corbin wrote:

My best guess is that you aren’t saving/restoring device state properly.

How this can be? From the serial driver POV, all C states are invisible, these are subset of P0 and do not cause the usual Sx-Dx transitions. Except, maybe, on those new, weird, highly integrated SoCs …

More testing is always a good idea, but if locking out Cx states helps, and the customer agrees - why not? It may be not his bug. However the serial driver should not do this itself. The OP can make additional simple usermode service. The customer will decide when to run it. One should not cramp everything into a kernel driver. What if customer wants a nice desktop background? This is OK, but not in the driver.

Having said this… if C states can be disabled, there’s a reason for it. And doing this from kernel should be possible. Like setting the timer resolution.

– pa

Perhaps the hardware has something like a latency timer and that’s how
things can fail ? Changing C states can take a lot of time on certain
processor models.

//Daniel

On Jan 12, 2017, at 6:38 AM, xxxxx@gmail.com wrote:

Thank you for the replies! Yes, the driver is interrupt driven, not polled. And when I say buffered, it reads and writes blocks of characters at a time, not just one character at a time. As for what is failing exactly, I am still waiting for the customer to provide that information. Their initial request was to disable C states in the driver due to failing at high baud rates, and that is what I was looking into.

That proposal is not reasonable. Let me give you an analogy. What you’re asking is similar to saying “I have a flat tire on my car. Can someone help me replace the engine with a smaller one so I can’t go as fast? It’s dangerous to go fast with a flat tire.”

You need to fix the problem in the driver. Attempting “fixes” at random without knowing the root cause is just going to do more harm than good.

Tim Roberts, xxxxx@probo.com
Providenza & Boekelheide, Inc.

“Please help me. The wings keep falling off my pig. Is it wrong to use super glue to attach the wings?”

http:

Peter
OSR
@OSRDrivers</http:>

Thanks again all! Further complicating this is that their first language is not English. So, there is often a disconnect. I agree, this needs to be analyzed more. My first thought was that the processor was not pulling characters fast enough out of the buffer. If they are using software flow control the halt character might not get there before data is overwritten. Hardware flow control might resolve this. If characters are getting overwritten before it gets to our driver, is that the fault of our driver? Assuming this is what’s happening.

I will check sleep states in the driver. And I will look into a latency timer. I also considered suggesting an app to turn off C states. I am in the investigation stage at this point and trying to figure out all of my options.

Tom Rubino wrote:

My first thought was that the processor was not pulling characters
fast enough out of the buffer.

Did you read what Tim said? Tim’s our resident expert on bus speeds (glug, glug) and you would do well to read and understand what he said.

xxxxx@gmail.com wrote:

My first thought was that the processor was not pulling characters fast enough out of the buffer. If they are using software flow control the halt character might not get there before data is overwritten. Hardware flow control might resolve this. If characters are getting overwritten before it gets to our driver, is that the fault of our driver? Assuming this is what’s happening.

There is zero chance that this is the problem. Remember, the processor
can execute 300,000 instructions between each byte. How have you
configured the interrupts? In many cases, you can configure how full
the buffer has to be before firing the interrupt. If you wait until the
buffer is completely full, that would be much worse than interrupting
when the buffer is NEARLY full.


Tim Roberts, xxxxx@probo.com
Providenza & Boekelheide, Inc.

> There is zero chance that this is the problem. Remember, the processor can execute 300,000 instructions between each byte. How have you configured the interrupts? In many cases, you can configure how full the buffer has to be before firing the interrupt. If you wait until the buffer is completely full, that would be much worse than interrupting when the buffer is NEARLY full.

OK, thanks Tim, I will look into that.