1/* 2 * Copyright (c) 2007 Apple Inc. All rights reserved. 3 * 4 * @APPLE_OSREFERENCE_LICENSE_HEADER_START@ 5 * 6 * This file contains Original Code and/or Modifications of Original Code 7 * as defined in and that are subject to the Apple Public Source License 8 * Version 2.0 (the 'License'). You may not use this file except in 9 * compliance with the License. The rights granted to you under the License 10 * may not be used to create, or enable the creation or redistribution of, 11 * unlawful or unlicensed copies of an Apple operating system, or to 12 * circumvent, violate, or enable the circumvention or violation of, any 13 * terms of an Apple operating system software license agreement. 14 * 15 * Please obtain a copy of the License at 16 * http://www.opensource.apple.com/apsl/ and read it before using this file. 17 * 18 * The Original Code and all software distributed under the License are 19 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER 20 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, 21 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, 22 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. 23 * Please see the License for the specific language governing rights and 24 * limitations under the License. 25 * 26 * @APPLE_OSREFERENCE_LICENSE_HEADER_END@ 27 */ 28 29#ifndef _IOKIT_IOSERVICEPMPRIVATE_H 30#define _IOKIT_IOSERVICEPMPRIVATE_H 31 32#include <IOKit/IOCommand.h> 33#include <IOKit/IOEventSource.h> 34 35//****************************************************************************** 36// PM command types 37//****************************************************************************** 38 39enum { 40 /* Command Types */ 41 kIOPMRequestTypeInvalid = 0x00, 42 kIOPMRequestTypePMStop = 0x01, 43 kIOPMRequestTypeAddPowerChild1 = 0x02, 44 kIOPMRequestTypeAddPowerChild2 = 0x03, 45 kIOPMRequestTypeAddPowerChild3 = 0x04, 46 kIOPMRequestTypeRegisterPowerDriver = 0x05, 47 kIOPMRequestTypeAdjustPowerState = 0x06, 48 kIOPMRequestTypePowerDomainWillChange = 0x07, 49 kIOPMRequestTypePowerDomainDidChange = 0x08, 50 kIOPMRequestTypePowerOverrideOnPriv = 0x09, 51 kIOPMRequestTypePowerOverrideOffPriv = 0x0A, 52 kIOPMRequestTypeActivityTickle = 0x0B, 53 kIOPMRequestTypeRequestPowerState = 0x0C, 54 kIOPMRequestTypeSynchronizePowerTree = 0x0D, 55 kIOPMRequestTypeRequestPowerStateOverride = 0x0E, 56 kIOPMRequestTypeSetIdleTimerPeriod = 0x0F, 57 kIOPMRequestTypeIgnoreIdleTimer = 0x10, 58 59 /* Reply Types */ 60 kIOPMRequestTypeReplyStart = 0x80, 61 kIOPMRequestTypeAckPowerChange = 0x81, 62 kIOPMRequestTypeAckSetPowerState = 0x82, 63 kIOPMRequestTypeAllowPowerChange = 0x83, 64 kIOPMRequestTypeCancelPowerChange = 0x84, 65 kIOPMRequestTypeInterestChanged = 0x85, 66 kIOPMRequestTypeIdleCancel = 0x86, 67 kIOPMRequestTypeChildNotifyDelayCancel = 0x87 68}; 69 70//****************************************************************************** 71// PM actions - For root domain only 72//****************************************************************************** 73 74struct IOPMActions; 75 76typedef void 77(*IOPMActionPowerChangeStart)( 78 void * target, 79 IOService * service, 80 IOPMActions * actions, 81 IOPMPowerStateIndex powerState, 82 IOPMPowerChangeFlags * changeFlags, 83 IOPMRequestTag requestTag ); 84 85typedef void 86(*IOPMActionPowerChangeDone)( 87 void * target, 88 IOService * service, 89 IOPMActions * actions, 90 IOPMPowerStateIndex powerState, 91 IOPMPowerChangeFlags changeFlags, 92 IOPMRequestTag requestTag ); 93 94typedef void 95(*IOPMActionPowerChangeOverride)( 96 void * target, 97 IOService * service, 98 IOPMActions * actions, 99 IOPMPowerStateIndex * powerState, 100 IOPMPowerChangeFlags * changeFlags, 101 IOPMRequestTag requestTag ); 102 103typedef void 104(*IOPMActionActivityTickle)( 105 void * target, 106 IOService * service, 107 IOPMActions * actions ); 108 109typedef void 110(*IOPMActionUpdatePowerClient)( 111 void * target, 112 IOService * service, 113 IOPMActions * actions, 114 const OSSymbol * powerClient, 115 IOPMPowerStateIndex oldPowerState, 116 IOPMPowerStateIndex newPowerState 117); 118 119struct IOPMActions { 120 void * target; 121 uint32_t parameter; 122 IOPMActionPowerChangeStart actionPowerChangeStart; 123 IOPMActionPowerChangeDone actionPowerChangeDone; 124 IOPMActionPowerChangeOverride actionPowerChangeOverride; 125 IOPMActionActivityTickle actionActivityTickle; 126 IOPMActionUpdatePowerClient actionUpdatePowerClient; 127}; 128 129// IOPMActions parameter flags 130enum { 131 kPMActionsFlagIsDisplayWrangler = 0x00000100, 132 kPMActionsFlagIsGraphicsDevice = 0x00000200, 133 kPMActionsFlagIsAudioDevice = 0x00000400, 134 kPMActionsFlagLimitPower = 0x00000800, 135 kPMActionsPCIBitNumberMask = 0x000000ff 136}; 137 138//****************************************************************************** 139// Internal concise representation of IOPMPowerState 140struct IOPMPSEntry 141{ 142 IOPMPowerFlags capabilityFlags; 143 IOPMPowerFlags outputPowerFlags; 144 IOPMPowerFlags inputPowerFlags; 145 uint32_t staticPower; 146 uint32_t settleUpTime; 147 uint32_t settleDownTime; 148 IOPMPowerStateIndex stateOrder; 149 IOPMPowerStateIndex stateOrderToIndex; 150}; 151 152//****************************************************************************** 153// IOServicePM 154//****************************************************************************** 155 156class IOServicePM : public OSObject 157{ 158 friend class IOService; 159 friend class IOPMWorkQueue; 160 161 OSDeclareDefaultStructors( IOServicePM ) 162 163private: 164 // Link IOServicePM objects on IOPMWorkQueue. 165 queue_chain_t WorkChain; 166 167 // Queue of IOPMRequest objects. 168 queue_head_t RequestHead; 169 170 // IOService creator and owner. 171 IOService * Owner; 172 173 // List of interested drivers (protected by PMLock). 174 IOPMinformeeList * InterestedDrivers; 175 176 // How long to wait for controlling driver to acknowledge. 177 IOReturn DriverTimer; 178 179 // Current power management machine state. 180 uint32_t MachineState; 181 182 thread_call_t AckTimer; 183 thread_call_t SettleTimer; 184 thread_call_t IdleTimer; 185 thread_call_t WatchdogTimer; 186 187 // Settle time after changing power state. 188 uint32_t SettleTimeUS; 189 uint32_t IdleTimerGeneration; 190 191 // The flags describing current change note. 192 IOPMPowerChangeFlags HeadNoteChangeFlags; 193 194 // The new power state number being changed to. 195 IOPMPowerStateIndex HeadNotePowerState; 196 197 // Points to the entry in the power state array. 198 IOPMPSEntry * HeadNotePowerArrayEntry; 199 200 // Power flags supplied by all parents (domain). 201 IOPMPowerFlags HeadNoteDomainFlags; 202 203 // Power flags supplied by domain accounting for parent changes. 204 IOPMPowerFlags HeadNoteDomainTargetFlags; 205 206 // Connection attached to the changing parent. 207 IOPowerConnection * HeadNoteParentConnection; 208 209 // Power flags supplied by the changing parent. 210 IOPMPowerFlags HeadNoteParentFlags; 211 212 // Number of acks still outstanding. 213 uint32_t HeadNotePendingAcks; 214 215 // PM state lock. 216 IOLock * PMLock; 217 218 unsigned int InitialPowerChange :1; 219 unsigned int InitialSetPowerState :1; 220 unsigned int DeviceOverrideEnabled :1; 221 unsigned int DoNotPowerDown :1; 222 unsigned int ParentsKnowState :1; 223 unsigned int StrictTreeOrder :1; 224 unsigned int IdleTimerStopped :1; 225 unsigned int AdjustPowerScheduled :1; 226 227 unsigned int IsPreChange :1; 228 unsigned int DriverCallBusy :1; 229 unsigned int PCDFunctionOverride :1; 230 unsigned int IdleTimerIgnored :1; 231 unsigned int HasAdvisoryDesire :1; 232 unsigned int AdvisoryTickleUsed :1; 233 unsigned int ResetPowerStateOnWake :1; 234 235 // Time of last device activity. 236 AbsoluteTime DeviceActiveTimestamp; 237 AbsoluteTime MaxPowerStateEntryTime; 238 AbsoluteTime MaxPowerStateExitTime; 239 240 // Used to protect activity flag. 241 IOLock * ActivityLock; 242 243 // Idle timer's period in seconds. 244 unsigned long IdleTimerPeriod; 245 unsigned long IdleTimerMinPowerState; 246 unsigned long NextIdleTimerPeriod; 247 AbsoluteTime IdleTimerStartTime; 248 249 // Power state desired by a subclassed device object. 250 IOPMPowerStateIndex DeviceDesire; 251 252 // This is the power state we desire currently. 253 IOPMPowerStateIndex DesiredPowerState; 254 255 // This is what our parent thinks our need is. 256 IOPMPowerFlags PreviousRequestPowerFlags; 257 258 // Cache result from getName(), used in logging. 259 const char * Name; 260 261 // Number of power states in the power array. 262 IOPMPowerStateIndex NumberOfPowerStates; 263 264 // Ordered highest power state in the power array. 265 IOPMPowerStateIndex HighestPowerState; 266 267 // Power state array. 268 IOPMPSEntry * PowerStates; 269 270 // The controlling driver. 271 IOService * ControllingDriver; 272 273 // Our current power state. 274 IOPMPowerStateIndex CurrentPowerState; 275 276 // Logical OR of power flags for each power domain parent. 277 IOPMPowerFlags ParentsCurrentPowerFlags; 278 279 // The highest power state we can achieve in current power domain. 280 IOPMPowerStateIndex MaxPowerState; 281 282 // Logical OR of all output power flags in the power state array. 283 IOPMPowerFlags MergedOutputPowerFlags; 284 285 // OSArray which manages responses from notified apps and clients. 286 OSArray * ResponseArray; 287 OSArray * NotifyClientArray; 288 289 // Used to uniquely identify power management notification to apps and clients. 290 UInt16 SerialNumber; 291 292 // Used to communicate desired function to tellClientsWithResponse(). 293 // This is used because it avoids changing the signatures of the affected virtual methods. 294 int OutOfBandParameter; 295 296 AbsoluteTime DriverCallStartTime; 297 IOPMPowerFlags CurrentCapabilityFlags; 298 unsigned long CurrentPowerConsumption; 299 IOPMPowerStateIndex TempClampPowerState; 300 OSArray * NotifyChildArray; 301 OSDictionary * PowerClients; 302 thread_call_t DriverCallEntry; 303 void * DriverCallParamPtr; 304 IOItemCount DriverCallParamCount; 305 IOItemCount DriverCallParamSlots; 306 uint32_t DriverCallReason; 307 uint32_t OutOfBandMessage; 308 uint32_t TempClampCount; 309 uint32_t OverrideMaxPowerState; 310 uint32_t DeviceUsablePowerState; 311 312 // Protected by ActivityLock - BEGIN 313 IOPMPowerStateIndex ActivityTicklePowerState; 314 IOPMPowerStateIndex AdvisoryTicklePowerState; 315 uint32_t ActivityTickleCount; 316 uint32_t DeviceWasActive : 1; 317 uint32_t AdvisoryTickled : 1; 318 // Protected by ActivityLock - END 319 320 uint32_t WaitReason; 321 uint32_t SavedMachineState; 322 323 // Protected by PMLock - BEGIN 324 struct { 325 uint32_t PMStop : 1; 326 uint32_t PMDriverCallWait : 1; 327 } LockedFlags; 328 329 queue_head_t PMDriverCallQueue; 330 OSSet * InsertInterestSet; 331 OSSet * RemoveInterestSet; 332 333 // IOReporter Data 334 uint32_t ReportClientCnt; 335 void * ReportBuf; 336 // Protected by PMLock - END 337 338#if PM_VARS_SUPPORT 339 IOPMprot * PMVars; 340#endif 341 342 IOPMActions PMActions; 343 344 // Serialize IOServicePM state for debug output. 345 IOReturn gatedSerialize( OSSerialize * s ) const; 346 virtual bool serialize( OSSerialize * s ) const; 347 348 // PM log and trace 349 void pmPrint( uint32_t event, uintptr_t param1, uintptr_t param2 ) const; 350 void pmTrace( uint32_t event, uintptr_t param1, uintptr_t param2 ) const; 351}; 352 353#define fOwner pwrMgt->Owner 354#define fInterestedDrivers pwrMgt->InterestedDrivers 355#define fDriverTimer pwrMgt->DriverTimer 356#define fMachineState pwrMgt->MachineState 357#define fAckTimer pwrMgt->AckTimer 358#define fSettleTimer pwrMgt->SettleTimer 359#define fIdleTimer pwrMgt->IdleTimer 360#define fWatchdogTimer pwrMgt->WatchdogTimer 361#define fSettleTimeUS pwrMgt->SettleTimeUS 362#define fIdleTimerGeneration pwrMgt->IdleTimerGeneration 363#define fHeadNoteChangeFlags pwrMgt->HeadNoteChangeFlags 364#define fHeadNotePowerState pwrMgt->HeadNotePowerState 365#define fHeadNotePowerArrayEntry pwrMgt->HeadNotePowerArrayEntry 366#define fHeadNoteDomainFlags pwrMgt->HeadNoteDomainFlags 367#define fHeadNoteDomainTargetFlags pwrMgt->HeadNoteDomainTargetFlags 368#define fHeadNoteParentConnection pwrMgt->HeadNoteParentConnection 369#define fHeadNoteParentFlags pwrMgt->HeadNoteParentFlags 370#define fHeadNotePendingAcks pwrMgt->HeadNotePendingAcks 371#define fPMLock pwrMgt->PMLock 372#define fInitialPowerChange pwrMgt->InitialPowerChange 373#define fInitialSetPowerState pwrMgt->InitialSetPowerState 374#define fDeviceOverrideEnabled pwrMgt->DeviceOverrideEnabled 375#define fDoNotPowerDown pwrMgt->DoNotPowerDown 376#define fParentsKnowState pwrMgt->ParentsKnowState 377#define fStrictTreeOrder pwrMgt->StrictTreeOrder 378#define fIdleTimerStopped pwrMgt->IdleTimerStopped 379#define fAdjustPowerScheduled pwrMgt->AdjustPowerScheduled 380#define fIsPreChange pwrMgt->IsPreChange 381#define fDriverCallBusy pwrMgt->DriverCallBusy 382#define fPCDFunctionOverride pwrMgt->PCDFunctionOverride 383#define fIdleTimerIgnored pwrMgt->IdleTimerIgnored 384#define fHasAdvisoryDesire pwrMgt->HasAdvisoryDesire 385#define fAdvisoryTickleUsed pwrMgt->AdvisoryTickleUsed 386#define fResetPowerStateOnWake pwrMgt->ResetPowerStateOnWake 387#define fDeviceActiveTimestamp pwrMgt->DeviceActiveTimestamp 388#define fMaxPowerStateEntryTime pwrMgt->MaxPowerStateEntryTime 389#define fMaxPowerStateExitTime pwrMgt->MaxPowerStateExitTime 390#define fActivityLock pwrMgt->ActivityLock 391#define fIdleTimerPeriod pwrMgt->IdleTimerPeriod 392#define fIdleTimerMinPowerState pwrMgt->IdleTimerMinPowerState 393#define fNextIdleTimerPeriod pwrMgt->NextIdleTimerPeriod 394#define fIdleTimerStartTime pwrMgt->IdleTimerStartTime 395#define fDeviceDesire pwrMgt->DeviceDesire 396#define fDesiredPowerState pwrMgt->DesiredPowerState 397#define fPreviousRequestPowerFlags pwrMgt->PreviousRequestPowerFlags 398#define fName pwrMgt->Name 399#define fNumberOfPowerStates pwrMgt->NumberOfPowerStates 400#define fHighestPowerState pwrMgt->HighestPowerState 401#define fPowerStates pwrMgt->PowerStates 402#define fControllingDriver pwrMgt->ControllingDriver 403#define fCurrentPowerState pwrMgt->CurrentPowerState 404#define fParentsCurrentPowerFlags pwrMgt->ParentsCurrentPowerFlags 405#define fMaxPowerState pwrMgt->MaxPowerState 406#define fMergedOutputPowerFlags pwrMgt->MergedOutputPowerFlags 407#define fResponseArray pwrMgt->ResponseArray 408#define fNotifyClientArray pwrMgt->NotifyClientArray 409#define fSerialNumber pwrMgt->SerialNumber 410#define fOutOfBandParameter pwrMgt->OutOfBandParameter 411#define fDriverCallStartTime pwrMgt->DriverCallStartTime 412#define fCurrentCapabilityFlags pwrMgt->CurrentCapabilityFlags 413#define fCurrentPowerConsumption pwrMgt->CurrentPowerConsumption 414#define fTempClampPowerState pwrMgt->TempClampPowerState 415#define fNotifyChildArray pwrMgt->NotifyChildArray 416#define fPowerClients pwrMgt->PowerClients 417#define fDriverCallEntry pwrMgt->DriverCallEntry 418#define fDriverCallParamPtr pwrMgt->DriverCallParamPtr 419#define fDriverCallParamCount pwrMgt->DriverCallParamCount 420#define fDriverCallParamSlots pwrMgt->DriverCallParamSlots 421#define fDriverCallReason pwrMgt->DriverCallReason 422#define fOutOfBandMessage pwrMgt->OutOfBandMessage 423#define fTempClampCount pwrMgt->TempClampCount 424#define fOverrideMaxPowerState pwrMgt->OverrideMaxPowerState 425#define fDeviceUsablePowerState pwrMgt->DeviceUsablePowerState 426#define fActivityTicklePowerState pwrMgt->ActivityTicklePowerState 427#define fAdvisoryTicklePowerState pwrMgt->AdvisoryTicklePowerState 428#define fActivityTickleCount pwrMgt->ActivityTickleCount 429#define fDeviceWasActive pwrMgt->DeviceWasActive 430#define fAdvisoryTickled pwrMgt->AdvisoryTickled 431#define fWaitReason pwrMgt->WaitReason 432#define fSavedMachineState pwrMgt->SavedMachineState 433#define fLockedFlags pwrMgt->LockedFlags 434#define fPMDriverCallQueue pwrMgt->PMDriverCallQueue 435#define fInsertInterestSet pwrMgt->InsertInterestSet 436#define fRemoveInterestSet pwrMgt->RemoveInterestSet 437#define fReportClientCnt pwrMgt->ReportClientCnt 438#define fReportBuf pwrMgt->ReportBuf 439#define fPMVars pwrMgt->PMVars 440#define fPMActions pwrMgt->PMActions 441 442#define StateOrder(state) (((state) < fNumberOfPowerStates) \ 443 ? pwrMgt->PowerStates[(state)].stateOrder \ 444 : (state)) 445#define StateMax(a,b) (StateOrder((a)) < StateOrder((b)) ? (b) : (a)) 446#define StateMin(a,b) (StateOrder((a)) < StateOrder((b)) ? (a) : (b)) 447 448#define kPowerStateZero (0) 449 450/* 451When an IOService is waiting for acknowledgement to a power change 452notification from an interested driver or the controlling driver, 453the ack timer is ticking every tenth of a second. 454(100000000 nanoseconds are one tenth of a second). 455*/ 456#define ACK_TIMER_PERIOD 100000000 457 458#define WATCHDOG_TIMER_PERIOD (300) // 300 secs 459 460// Max wait time in microseconds for kernel priority and capability clients 461// with async message handlers to acknowledge. 462// 463#define kPriorityClientMaxWait (90 * 1000 * 1000) 464#define kCapabilityClientMaxWait (240 * 1000 * 1000) 465 466// Attributes describing a power state change. 467// See IOPMPowerChangeFlags data type. 468// 469#define kIOPMParentInitiated 0x0001 // power change initiated by our parent 470#define kIOPMSelfInitiated 0x0002 // power change initiated by this device 471#define kIOPMNotDone 0x0004 // we couldn't make this change 472#define kIOPMDomainWillChange 0x0008 // change started by PowerDomainWillChangeTo 473#define kIOPMDomainDidChange 0x0010 // change started by PowerDomainDidChangeTo 474#define kIOPMDomainPowerDrop 0x0020 // Domain is lowering power 475#define kIOPMIgnoreChildren 0x0040 // Ignore children and driver power desires 476#define kIOPMSkipAskPowerDown 0x0080 // skip the ask app phase 477#define kIOPMSynchronize 0x0100 // change triggered by power tree re-sync 478#define kIOPMSyncNoChildNotify 0x0200 // sync root domain only, not entire tree 479#define kIOPMSyncTellPowerDown 0x0400 // send the ask/will power off messages 480#define kIOPMSyncCancelPowerDown 0x0800 // sleep cancel for maintenance wake 481#define kIOPMInitialPowerChange 0x1000 // set for initial power change 482#define kIOPMRootChangeUp 0x2000 // Root power domain change up 483#define kIOPMRootChangeDown 0x4000 // Root power domain change down 484#define kIOPMExpireIdleTimer 0x8000 // Accelerate idle timer expiration 485 486#define kIOPMRootBroadcastFlags (kIOPMSynchronize | \ 487 kIOPMRootChangeUp | kIOPMRootChangeDown) 488 489// Activity tickle request flags 490#define kTickleTypePowerDrop 0x01 491#define kTickleTypePowerRise 0x02 492#define kTickleTypeActivity 0x04 493#define kTickleTypeAdvisory 0x08 494 495enum { 496 kDriverCallInformPreChange, 497 kDriverCallInformPostChange, 498 kDriverCallSetPowerState, 499 kRootDomainInformPreChange 500}; 501 502struct DriverCallParam { 503 OSObject * Target; 504 IOReturn Result; 505}; 506 507// values of OutOfBandParameter 508enum { 509 kNotifyApps, 510 kNotifyPriority, 511 kNotifyCapabilityChangeApps, 512 kNotifyCapabilityChangePriority 513}; 514 515typedef bool (*IOPMMessageFilter)( 516 void * target, void * object, void * arg1, void * arg2, void * arg3 ); 517 518// used for applyToInterested 519struct IOPMInterestContext { 520 OSArray * responseArray; 521 OSArray * notifyClients; 522 uint16_t serialNumber; 523 uint8_t isPreChange; 524 uint8_t enableTracing; 525 uint32_t maxTimeRequested; 526 uint32_t messageType; 527 uint32_t notifyType; 528 IOService * us; 529 IOPMPowerStateIndex stateNumber; 530 IOPMPowerFlags stateFlags; 531 IOPMPowerChangeFlags changeFlags; 532 const char * errorLog; 533 IOPMMessageFilter messageFilter; 534}; 535 536// assertPMDriverCall() options 537enum { 538 kIOPMADC_NoInactiveCheck = 1 539}; 540 541//****************************************************************************** 542// PM Statistics & Diagnostics 543//****************************************************************************** 544 545extern const OSSymbol *gIOPMStatsApplicationResponseTimedOut; 546extern const OSSymbol *gIOPMStatsApplicationResponseCancel; 547extern const OSSymbol *gIOPMStatsApplicationResponseSlow; 548extern const OSSymbol *gIOPMStatsApplicationResponsePrompt; 549extern const OSSymbol *gIOPMStatsDriverPSChangeSlow; 550 551//****************************************************************************** 552// IOPMRequest 553//****************************************************************************** 554 555typedef void (*IOPMCompletionAction)(void * target, void * param, IOReturn status); 556 557class IOPMRequest : public IOCommand 558{ 559 OSDeclareDefaultStructors( IOPMRequest ) 560 561protected: 562 IOService * fTarget; // request target 563 IOPMRequest * fRequestNext; // the next request in the chain 564 IOPMRequest * fRequestRoot; // the root request in the issue tree 565 IOItemCount fWorkWaitCount; // execution blocked if non-zero 566 IOItemCount fFreeWaitCount; // completion blocked if non-zero 567 uint32_t fType; // request type 568 569#if NOT_READY 570 IOPMCompletionAction fCompletionAction; 571 void * fCompletionTarget; 572 void * fCompletionParam; 573 IOReturn fCompletionStatus; 574#endif 575 576public: 577 uint32_t fRequestTag; 578 void * fArg0; 579 void * fArg1; 580 void * fArg2; 581 582 inline bool isWorkBlocked( void ) const 583 { 584 return (fWorkWaitCount != 0); 585 } 586 587 inline bool isFreeBlocked( void ) const 588 { 589 return (fFreeWaitCount != 0); 590 } 591 592 inline IOPMRequest * getNextRequest( void ) const 593 { 594 return fRequestNext; 595 } 596 597 inline IOPMRequest * getRootRequest( void ) const 598 { 599 if (fRequestRoot) return fRequestRoot; 600#if NOT_READY 601 if (fCompletionAction) return (IOPMRequest *) this; 602#endif 603 return 0; 604 } 605 606 inline uint32_t getType( void ) const 607 { 608 return fType; 609 } 610 611 inline bool isReplyType( void ) const 612 { 613 return (fType > kIOPMRequestTypeReplyStart); 614 } 615 616 inline IOService * getTarget( void ) const 617 { 618 return fTarget; 619 } 620 621#if NOT_READY 622 inline bool isCompletionInstalled( void ) 623 { 624 return (fCompletionAction != 0); 625 } 626 627 inline void installCompletionAction( 628 IOPMCompletionAction action, 629 void * target, 630 void * param ) 631 { 632 fCompletionAction = action; 633 fCompletionTarget = target; 634 fCompletionParam = param; 635 } 636#endif /* NOT_READY */ 637 638 static IOPMRequest * create( void ); 639 bool init( IOService * owner, IOOptionBits type ); 640 void reset( void ); 641 bool attachNextRequest( IOPMRequest * next ); 642 bool detachNextRequest( void ); 643 bool attachRootRequest( IOPMRequest * root ); 644 bool detachRootRequest( void ); 645}; 646 647//****************************************************************************** 648// IOPMRequestQueue 649//****************************************************************************** 650 651class IOPMRequestQueue : public IOEventSource 652{ 653 OSDeclareDefaultStructors( IOPMRequestQueue ) 654 655public: 656 typedef bool (*Action)( IOService *, IOPMRequest *, IOPMRequestQueue * ); 657 658protected: 659 queue_head_t fQueue; 660 IOLock * fLock; 661 662 virtual bool checkForWork( void ); 663 virtual void free( void ); 664 virtual bool init( IOService * inOwner, Action inAction ); 665 666public: 667 static IOPMRequestQueue * create( IOService * inOwner, Action inAction ); 668 void queuePMRequest( IOPMRequest * request ); 669 void queuePMRequestChain( IOPMRequest ** requests, IOItemCount count ); 670}; 671 672//****************************************************************************** 673// IOPMWorkQueue 674//****************************************************************************** 675 676#define WORK_QUEUE_STATS 1 677 678class IOPMWorkQueue : public IOEventSource 679{ 680 OSDeclareDefaultStructors( IOPMWorkQueue ) 681 682public: 683 typedef bool (*Action)( IOService *, IOPMRequest *, IOPMWorkQueue * ); 684 685#if WORK_QUEUE_STATS 686 uint64_t fStatCheckForWork; 687 uint64_t fStatScanEntries; 688 uint64_t fStatQueueEmpty; 689 uint64_t fStatNoWorkDone; 690#endif 691 692protected: 693 queue_head_t fWorkQueue; 694 Action fWorkAction; 695 Action fRetireAction; 696 uint32_t fQueueLength; 697 uint32_t fConsumerCount; 698 volatile uint32_t fProducerCount; 699 700 virtual bool checkForWork( void ); 701 virtual bool init( IOService * inOwner, Action work, Action retire ); 702 bool checkRequestQueue( queue_head_t * queue, bool * empty ); 703 704public: 705 static IOPMWorkQueue * create( IOService * inOwner, Action work, Action retire ); 706 bool queuePMRequest( IOPMRequest * request, IOServicePM * pwrMgt ); 707 void signalWorkAvailable( void ); 708 void incrementProducerCount( void ); 709}; 710 711//****************************************************************************** 712// IOPMCompletionQueue 713//****************************************************************************** 714 715class IOPMCompletionQueue : public IOEventSource 716{ 717 OSDeclareDefaultStructors( IOPMCompletionQueue ) 718 719public: 720 typedef bool (*Action)( IOService *, IOPMRequest *, IOPMCompletionQueue * ); 721 722protected: 723 queue_head_t fQueue; 724 725 virtual bool checkForWork( void ); 726 virtual bool init( IOService * inOwner, Action inAction ); 727 728public: 729 static IOPMCompletionQueue * create( IOService * inOwner, Action inAction ); 730 bool queuePMRequest( IOPMRequest * request ); 731}; 732 733#endif /* !_IOKIT_IOSERVICEPMPRIVATE_H */ 734