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