X-Git-Url: https://git.saurik.com/apple/xnu.git/blobdiff_plain/6d2010ae8f7a6078e10b361c6962983bab233e0f..bb59bff194111743b33cc36712410b5656329d3c:/iokit/Kernel/IOServicePMPrivate.h diff --git a/iokit/Kernel/IOServicePMPrivate.h b/iokit/Kernel/IOServicePMPrivate.h index 96e5bfacc..313d8e3c5 100644 --- a/iokit/Kernel/IOServicePMPrivate.h +++ b/iokit/Kernel/IOServicePMPrivate.h @@ -54,7 +54,8 @@ enum { kIOPMRequestTypeSynchronizePowerTree = 0x0D, kIOPMRequestTypeRequestPowerStateOverride = 0x0E, kIOPMRequestTypeSetIdleTimerPeriod = 0x0F, - + kIOPMRequestTypeIgnoreIdleTimer = 0x10, + /* Reply Types */ kIOPMRequestTypeReplyStart = 0x80, kIOPMRequestTypeAckPowerChange = 0x81, @@ -74,33 +75,46 @@ struct IOPMActions; typedef void (*IOPMActionPowerChangeStart)( - void * target, - IOService * service, - IOPMActions * actions, - uint32_t powerState, - uint32_t * changeFlags ); + void * target, + IOService * service, + IOPMActions * actions, + IOPMPowerStateIndex powerState, + IOPMPowerChangeFlags * changeFlags, + IOPMRequestTag requestTag ); typedef void (*IOPMActionPowerChangeDone)( - void * target, - IOService * service, - IOPMActions * actions, - uint32_t powerState, - uint32_t changeFlags ); + void * target, + IOService * service, + IOPMActions * actions, + IOPMPowerStateIndex powerState, + IOPMPowerChangeFlags changeFlags, + IOPMRequestTag requestTag ); typedef void (*IOPMActionPowerChangeOverride)( - void * target, - IOService * service, - IOPMActions * actions, - unsigned long * powerState, - uint32_t * changeFlags ); + void * target, + IOService * service, + IOPMActions * actions, + IOPMPowerStateIndex * powerState, + IOPMPowerChangeFlags * changeFlags, + IOPMRequestTag requestTag ); typedef void (*IOPMActionActivityTickle)( - void * target, - IOService * service, - IOPMActions * actions ); + void * target, + IOService * service, + IOPMActions * actions ); + +typedef void +(*IOPMActionUpdatePowerClient)( + void * target, + IOService * service, + IOPMActions * actions, + const OSSymbol * powerClient, + IOPMPowerStateIndex oldPowerState, + IOPMPowerStateIndex newPowerState +); struct IOPMActions { void * target; @@ -109,59 +123,30 @@ struct IOPMActions { IOPMActionPowerChangeDone actionPowerChangeDone; IOPMActionPowerChangeOverride actionPowerChangeOverride; IOPMActionActivityTickle actionActivityTickle; + IOPMActionUpdatePowerClient actionUpdatePowerClient; }; -//****************************************************************************** - +// IOPMActions parameter flags enum { - kIOPMEventClassSystemEvent = 0x00, - kIOPMEventClassDriverEvent = 0x1 -}; - -class PMEventDetails : public OSObject -{ - OSDeclareDefaultStructors( PMEventDetails ); - friend class IOServicePM; - friend class IOPMrootDomain; - friend class IOPMTimeline; -public: - static PMEventDetails *eventDetails(uint32_t type, - const char *ownerName, - uintptr_t ownerUnique, - const char *interestName, - uint8_t oldState, - uint8_t newState, - uint32_t result, - uint32_t elapsedTimeUS); - - static PMEventDetails *eventDetails(uint32_t type, - const char *uuid, - uint32_t reason, - uint32_t result); -private: - uint8_t eventClassifier; - uint32_t eventType; - const char *ownerName; - uintptr_t ownerUnique; - const char *interestName; - uint8_t oldState; - uint8_t newState; - uint32_t result; - uint32_t elapsedTimeUS; - - const char *uuid; - uint32_t reason; + kPMActionsFlagIsDisplayWrangler = 0x00000100, + kPMActionsFlagIsGraphicsDevice = 0x00000200, + kPMActionsFlagIsAudioDevice = 0x00000400, + kPMActionsFlagLimitPower = 0x00000800, + kPMActionsPCIBitNumberMask = 0x000000ff }; +//****************************************************************************** // Internal concise representation of IOPMPowerState struct IOPMPSEntry { - IOPMPowerFlags capabilityFlags; - IOPMPowerFlags outputPowerFlags; - IOPMPowerFlags inputPowerFlags; - uint32_t staticPower; - uint32_t settleUpTime; - uint32_t settleDownTime; + IOPMPowerFlags capabilityFlags; + IOPMPowerFlags outputPowerFlags; + IOPMPowerFlags inputPowerFlags; + uint32_t staticPower; + uint32_t settleUpTime; + uint32_t settleDownTime; + IOPMPowerStateIndex stateOrder; + IOPMPowerStateIndex stateOrderToIndex; }; //****************************************************************************** @@ -178,7 +163,7 @@ class IOServicePM : public OSObject private: // Link IOServicePM objects on IOPMWorkQueue. queue_chain_t WorkChain; - + // Queue of IOPMRequest objects. queue_head_t RequestHead; @@ -197,9 +182,11 @@ private: thread_call_t AckTimer; thread_call_t SettleTimer; thread_call_t IdleTimer; + thread_call_t WatchdogTimer; // Settle time after changing power state. uint32_t SettleTimeUS; + uint32_t IdleTimerGeneration; // The flags describing current change note. IOPMPowerChangeFlags HeadNoteChangeFlags; @@ -218,7 +205,7 @@ private: // Connection attached to the changing parent. IOPowerConnection * HeadNoteParentConnection; - + // Power flags supplied by the changing parent. IOPMPowerFlags HeadNoteParentFlags; @@ -228,21 +215,27 @@ private: // PM state lock. IOLock * PMLock; - unsigned int InitialPowerChange:1; - unsigned int InitialSetPowerState:1; - unsigned int DeviceOverrideEnabled:1; - unsigned int DeviceWasActive:1; - unsigned int DoNotPowerDown:1; - unsigned int ParentsKnowState:1; - unsigned int StrictTreeOrder:1; - unsigned int IdleTimerStopped:1; - unsigned int AdjustPowerScheduled:1; - unsigned int IsPreChange:1; - unsigned int DriverCallBusy:1; - unsigned int PCDFunctionOverride:1; + unsigned int InitialPowerChange :1; + unsigned int InitialSetPowerState :1; + unsigned int DeviceOverrideEnabled :1; + unsigned int DoNotPowerDown :1; + unsigned int ParentsKnowState :1; + unsigned int StrictTreeOrder :1; + unsigned int IdleTimerStopped :1; + unsigned int AdjustPowerScheduled :1; + + unsigned int IsPreChange :1; + unsigned int DriverCallBusy :1; + unsigned int PCDFunctionOverride :1; + unsigned int IdleTimerIgnored :1; + unsigned int HasAdvisoryDesire :1; + unsigned int AdvisoryTickleUsed :1; + unsigned int ResetPowerStateOnWake :1; // Time of last device activity. AbsoluteTime DeviceActiveTimestamp; + AbsoluteTime MaxPowerStateEntryTime; + AbsoluteTime MaxPowerStateExitTime; // Used to protect activity flag. IOLock * ActivityLock; @@ -250,6 +243,7 @@ private: // Idle timer's period in seconds. unsigned long IdleTimerPeriod; unsigned long IdleTimerMinPowerState; + unsigned long NextIdleTimerPeriod; AbsoluteTime IdleTimerStartTime; // Power state desired by a subclassed device object. @@ -267,6 +261,9 @@ private: // Number of power states in the power array. IOPMPowerStateIndex NumberOfPowerStates; + // Ordered highest power state in the power array. + IOPMPowerStateIndex HighestPowerState; + // Power state array. IOPMPSEntry * PowerStates; @@ -282,8 +279,8 @@ private: // The highest power state we can achieve in current power domain. IOPMPowerStateIndex MaxPowerState; - // Logical OR of all output power character flags in the array. - IOPMPowerFlags OutputPowerCharacterFlags; + // Logical OR of all output power flags in the power state array. + IOPMPowerFlags MergedOutputPowerFlags; // OSArray which manages responses from notified apps and clients. OSArray * ResponseArray; @@ -298,7 +295,6 @@ private: AbsoluteTime DriverCallStartTime; IOPMPowerFlags CurrentCapabilityFlags; - long ActivityTicklePowerState; unsigned long CurrentPowerConsumption; IOPMPowerStateIndex TempClampPowerState; OSArray * NotifyChildArray; @@ -311,10 +307,18 @@ private: uint32_t OutOfBandMessage; uint32_t TempClampCount; uint32_t OverrideMaxPowerState; + uint32_t DeviceUsablePowerState; + + // Protected by ActivityLock - BEGIN + IOPMPowerStateIndex ActivityTicklePowerState; + IOPMPowerStateIndex AdvisoryTicklePowerState; uint32_t ActivityTickleCount; + uint32_t DeviceWasActive : 1; + uint32_t AdvisoryTickled : 1; + // Protected by ActivityLock - END + uint32_t WaitReason; uint32_t SavedMachineState; - uint32_t RootDomainState; // Protected by PMLock - BEGIN struct { @@ -325,6 +329,10 @@ private: queue_head_t PMDriverCallQueue; OSSet * InsertInterestSet; OSSet * RemoveInterestSet; + + // IOReporter Data + uint32_t ReportClientCnt; + void * ReportBuf; // Protected by PMLock - END #if PM_VARS_SUPPORT @@ -334,8 +342,12 @@ private: IOPMActions PMActions; // Serialize IOServicePM state for debug output. - IOReturn gatedSerialize( OSSerialize * s ); + IOReturn gatedSerialize( OSSerialize * s ) const; virtual bool serialize( OSSerialize * s ) const; + + // PM log and trace + void pmPrint( uint32_t event, uintptr_t param1, uintptr_t param2 ) const; + void pmTrace( uint32_t event, uintptr_t param1, uintptr_t param2 ) const; }; #define fOwner pwrMgt->Owner @@ -345,7 +357,9 @@ private: #define fAckTimer pwrMgt->AckTimer #define fSettleTimer pwrMgt->SettleTimer #define fIdleTimer pwrMgt->IdleTimer +#define fWatchdogTimer pwrMgt->WatchdogTimer #define fSettleTimeUS pwrMgt->SettleTimeUS +#define fIdleTimerGeneration pwrMgt->IdleTimerGeneration #define fHeadNoteChangeFlags pwrMgt->HeadNoteChangeFlags #define fHeadNotePowerState pwrMgt->HeadNotePowerState #define fHeadNotePowerArrayEntry pwrMgt->HeadNotePowerArrayEntry @@ -358,7 +372,6 @@ private: #define fInitialPowerChange pwrMgt->InitialPowerChange #define fInitialSetPowerState pwrMgt->InitialSetPowerState #define fDeviceOverrideEnabled pwrMgt->DeviceOverrideEnabled -#define fDeviceWasActive pwrMgt->DeviceWasActive #define fDoNotPowerDown pwrMgt->DoNotPowerDown #define fParentsKnowState pwrMgt->ParentsKnowState #define fStrictTreeOrder pwrMgt->StrictTreeOrder @@ -367,29 +380,36 @@ private: #define fIsPreChange pwrMgt->IsPreChange #define fDriverCallBusy pwrMgt->DriverCallBusy #define fPCDFunctionOverride pwrMgt->PCDFunctionOverride +#define fIdleTimerIgnored pwrMgt->IdleTimerIgnored +#define fHasAdvisoryDesire pwrMgt->HasAdvisoryDesire +#define fAdvisoryTickleUsed pwrMgt->AdvisoryTickleUsed +#define fResetPowerStateOnWake pwrMgt->ResetPowerStateOnWake #define fDeviceActiveTimestamp pwrMgt->DeviceActiveTimestamp +#define fMaxPowerStateEntryTime pwrMgt->MaxPowerStateEntryTime +#define fMaxPowerStateExitTime pwrMgt->MaxPowerStateExitTime #define fActivityLock pwrMgt->ActivityLock #define fIdleTimerPeriod pwrMgt->IdleTimerPeriod #define fIdleTimerMinPowerState pwrMgt->IdleTimerMinPowerState +#define fNextIdleTimerPeriod pwrMgt->NextIdleTimerPeriod #define fIdleTimerStartTime pwrMgt->IdleTimerStartTime #define fDeviceDesire pwrMgt->DeviceDesire #define fDesiredPowerState pwrMgt->DesiredPowerState #define fPreviousRequestPowerFlags pwrMgt->PreviousRequestPowerFlags #define fName pwrMgt->Name #define fNumberOfPowerStates pwrMgt->NumberOfPowerStates +#define fHighestPowerState pwrMgt->HighestPowerState #define fPowerStates pwrMgt->PowerStates #define fControllingDriver pwrMgt->ControllingDriver #define fCurrentPowerState pwrMgt->CurrentPowerState #define fParentsCurrentPowerFlags pwrMgt->ParentsCurrentPowerFlags #define fMaxPowerState pwrMgt->MaxPowerState -#define fOutputPowerCharacterFlags pwrMgt->OutputPowerCharacterFlags +#define fMergedOutputPowerFlags pwrMgt->MergedOutputPowerFlags #define fResponseArray pwrMgt->ResponseArray #define fNotifyClientArray pwrMgt->NotifyClientArray #define fSerialNumber pwrMgt->SerialNumber #define fOutOfBandParameter pwrMgt->OutOfBandParameter #define fDriverCallStartTime pwrMgt->DriverCallStartTime #define fCurrentCapabilityFlags pwrMgt->CurrentCapabilityFlags -#define fActivityTicklePowerState pwrMgt->ActivityTicklePowerState #define fCurrentPowerConsumption pwrMgt->CurrentPowerConsumption #define fTempClampPowerState pwrMgt->TempClampPowerState #define fNotifyChildArray pwrMgt->NotifyChildArray @@ -402,17 +422,31 @@ private: #define fOutOfBandMessage pwrMgt->OutOfBandMessage #define fTempClampCount pwrMgt->TempClampCount #define fOverrideMaxPowerState pwrMgt->OverrideMaxPowerState +#define fDeviceUsablePowerState pwrMgt->DeviceUsablePowerState +#define fActivityTicklePowerState pwrMgt->ActivityTicklePowerState +#define fAdvisoryTicklePowerState pwrMgt->AdvisoryTicklePowerState #define fActivityTickleCount pwrMgt->ActivityTickleCount +#define fDeviceWasActive pwrMgt->DeviceWasActive +#define fAdvisoryTickled pwrMgt->AdvisoryTickled #define fWaitReason pwrMgt->WaitReason #define fSavedMachineState pwrMgt->SavedMachineState -#define fRootDomainState pwrMgt->RootDomainState #define fLockedFlags pwrMgt->LockedFlags #define fPMDriverCallQueue pwrMgt->PMDriverCallQueue #define fInsertInterestSet pwrMgt->InsertInterestSet #define fRemoveInterestSet pwrMgt->RemoveInterestSet +#define fReportClientCnt pwrMgt->ReportClientCnt +#define fReportBuf pwrMgt->ReportBuf #define fPMVars pwrMgt->PMVars #define fPMActions pwrMgt->PMActions +#define StateOrder(state) (((state) < fNumberOfPowerStates) \ + ? pwrMgt->PowerStates[(state)].stateOrder \ + : (state)) +#define StateMax(a,b) (StateOrder((a)) < StateOrder((b)) ? (b) : (a)) +#define StateMin(a,b) (StateOrder((a)) < StateOrder((b)) ? (a) : (b)) + +#define kPowerStateZero (0) + /* When an IOService is waiting for acknowledgement to a power change notification from an interested driver or the controlling driver, @@ -421,17 +455,19 @@ the ack timer is ticking every tenth of a second. */ #define ACK_TIMER_PERIOD 100000000 +#define WATCHDOG_TIMER_PERIOD (300) // 300 secs + // Max wait time in microseconds for kernel priority and capability clients // with async message handlers to acknowledge. -// +// #define kPriorityClientMaxWait (90 * 1000 * 1000) #define kCapabilityClientMaxWait (240 * 1000 * 1000) // Attributes describing a power state change. // See IOPMPowerChangeFlags data type. // -#define kIOPMParentInitiated 0x0001 // this power change initiated by our parent -#define kIOPMSelfInitiated 0x0002 // this power change initiated by this device +#define kIOPMParentInitiated 0x0001 // power change initiated by our parent +#define kIOPMSelfInitiated 0x0002 // power change initiated by this device #define kIOPMNotDone 0x0004 // we couldn't make this change #define kIOPMDomainWillChange 0x0008 // change started by PowerDomainWillChangeTo #define kIOPMDomainDidChange 0x0010 // change started by PowerDomainDidChangeTo @@ -442,11 +478,25 @@ the ack timer is ticking every tenth of a second. #define kIOPMSyncNoChildNotify 0x0200 // sync root domain only, not entire tree #define kIOPMSyncTellPowerDown 0x0400 // send the ask/will power off messages #define kIOPMSyncCancelPowerDown 0x0800 // sleep cancel for maintenance wake +#define kIOPMInitialPowerChange 0x1000 // set for initial power change +#define kIOPMRootChangeUp 0x2000 // Root power domain change up +#define kIOPMRootChangeDown 0x4000 // Root power domain change down +#define kIOPMExpireIdleTimer 0x8000 // Accelerate idle timer expiration + +#define kIOPMRootBroadcastFlags (kIOPMSynchronize | \ + kIOPMRootChangeUp | kIOPMRootChangeDown) + +// Activity tickle request flags +#define kTickleTypePowerDrop 0x01 +#define kTickleTypePowerRise 0x02 +#define kTickleTypeActivity 0x04 +#define kTickleTypeAdvisory 0x08 enum { kDriverCallInformPreChange, kDriverCallInformPostChange, - kDriverCallSetPowerState + kDriverCallSetPowerState, + kRootDomainInformPreChange }; struct DriverCallParam { @@ -495,6 +545,8 @@ enum { extern const OSSymbol *gIOPMStatsApplicationResponseTimedOut; extern const OSSymbol *gIOPMStatsApplicationResponseCancel; extern const OSSymbol *gIOPMStatsApplicationResponseSlow; +extern const OSSymbol *gIOPMStatsApplicationResponsePrompt; +extern const OSSymbol *gIOPMStatsDriverPSChangeSlow; //****************************************************************************** // IOPMRequest @@ -514,12 +566,15 @@ protected: IOItemCount fFreeWaitCount; // completion blocked if non-zero uint32_t fType; // request type +#if NOT_READY IOPMCompletionAction fCompletionAction; void * fCompletionTarget; void * fCompletionParam; IOReturn fCompletionStatus; +#endif public: + uint32_t fRequestTag; void * fArg0; void * fArg1; void * fArg2; @@ -542,7 +597,9 @@ public: inline IOPMRequest * getRootRequest( void ) const { if (fRequestRoot) return fRequestRoot; +#if NOT_READY if (fCompletionAction) return (IOPMRequest *) this; +#endif return 0; } @@ -561,6 +618,7 @@ public: return fTarget; } +#if NOT_READY inline bool isCompletionInstalled( void ) { return (fCompletionAction != 0); @@ -575,6 +633,7 @@ public: fCompletionTarget = target; fCompletionParam = param; } +#endif /* NOT_READY */ static IOPMRequest * create( void ); bool init( IOService * owner, IOOptionBits type );