Power Management

Describes the power management policies.

The MMC Controller manages the power to the MultiMediaCard hardware.

Normal power up and power down handling

Before card commands can be issued to a card, three operations are required:

  • power must be applied to the card, i.e. VDD must be turned on

  • any requirement from the power model must be set, e.g. requesting a necessary system clock

  • the clock to the card interface must be switched on.

All three operations are performed as part of the DMMCStack::CIMInitStackSM() state machine function which then issues the sequence of commands involved in performing the CIM_UPDATE_ACQ macro to initialize a card stack.

There are two cases:

  • Local drive requests, i.e. those originating from a media driver - if the card is not fully powered up when such a request is received, then the local media device driver automatically precedes the request with an instruction to the controller to power up the card. This results in DMMCSocket::InitiatePowerUpSequence() being called, which in turn invokes the DMMCStack::CIMInitStackSM() state machine function.

    Once the MultiMediaCard stack has been initialized, the MultiMediaCard controller calls DPBusSocket::PowerUpSequenceComplete() to signal the completion of initialization back to the local media driver, and this can then continue to open a media driver and continue with the original request.

    This automatic re-powering of the card applies in all situations which can lead to the card not being powered: media change, machine power down, card inactivity timeout, VDD power problem etc. In most cases, the process of restoring power results in the closure of any existing media driver and a new one opened. As the kernel thread used to perform controller requests is able to block, this means that no special mechanism is necessary to allow for this potential long-running power up sequence prior to a request on the device.

  • Requests not originating via a local media device driver, for example device drivers for I/O cards - if the MultiMediaCard stack is not initialized when the client submits a session, then the MultiMediaCard controller automatically precedes the request with a call to the DMMCStack::CIMInitStackSM() state machine function.

The MultiMediaCard controller will normally be configured with an inactivity timer. If a given period elapses where there is no bus activity, then the controller automatically turns off the card clock, removes any power requirements on the power model, and then removes power from the cards. This is the bus power down sequence. The length of this inactivity timeout period is set in the platform specific layer as part of porting the controller, and can be disabled completely if required; see the reference to porting the PsuInfo() function as part of implementing the DMMCPsu derived class.

Clients of the controller do not need to worry about re-initializing the stack following such a power down as the controller does this automatically.

In the event of a PSU voltage check failure, the controller performs the bus power down sequence. It will not re-power the problem card and will expect it to be removed.

The power model calls DPBusSocket::DoPowerDown() when the machine is about to be normally turned off (due to the off key being pressed or keyboard/touch screen inactivity). This leads to the function DMMCStack::PowerDownStack() being called resulting in the bus power down sequence.

When the machine is powered back up after a normal power off, the power model calls DPBusSocket::DoPowerUp(). However, the controller normally does not power up the bus, but waits for the next request from one of its clients before doing so. The only exception is where a card power up sequence was interrupted by the machine being turned off.

Emergency power down

In an emergency power down situation, for example, where a battery is in a critically low power state, the MultiMediaCard controller performs the normal bus power down sequence as this is not a lengthy operation. The power model calls DPBusSocket::DoEmergencyPowerDown(), which results in a call to DMMCStack::PowerDownStack().

However, there is always a risk that a block being written to a card may become corrupt. The solution to this problem lies in the hardware architecture. Two possible solutions are:

  • to provide enough early warning of power being removed before the battery level becomes too low for card operation. For example, a catch mechanism on a battery door, making it slow to remove. This would provide sufficient time for any write operation in progress to be terminated at the next block boundary before the power supply is lost.

    Note, however, that the media driver fails any operations involving write operations to a card when the battery level is becoming dangerously low, so in general, we are only talking about unexpected battery removal.

  • to provide a backup battery so that the failing write operation can be re-retried once a good battery level has been restored.

Even with such mechanisms in place, if power is removed in the middle of a multi-block write operation, then some blocks will contain new data while others will still contain old data.

Media change

When a door open event is detected by the MultiMediaCard controller, it attempts to remove power from a card as soon as possible. Power is not removed immediately if a bus operation is in progress as powering down a card in the middle of writing a block could leave the block corrupted.

Power is only removed from a card immediately a door open event occurs if there are no sessions queued by clients on the controller. If one or more sessions are queued then these are allowed to complete, with power being removed once the last session has completed. Any attempt to engage a new session while the door is open fails with KErrNotReady.

To prevent a card becoming corrupt because of attempted removal during a write operation, then it is important that the door mechanism and circuitry gives enough early warning of a potential card removal before the card is actually removed. This is to provide sufficient time for any write operation in progress to proceed to the next block boundary before the card is removed.

Once the door is closed again, then new sessions can be engaged and power can be re-applied to the card by the controller. However, power is only restored by the controller in response to a client request. The Controller does not automatically re-power a card to resume an operation interrupted by a door open event, no matter what operation was in progress when the door opened.