1*42e22086SApple OSS Distributions /* 2*42e22086SApple OSS Distributions * Copyright (c) 2011-2021 Apple Computer, Inc. All rights reserved. 3*42e22086SApple OSS Distributions * 4*42e22086SApple OSS Distributions * @APPLE_OSREFERENCE_LICENSE_HEADER_START@ 5*42e22086SApple OSS Distributions * 6*42e22086SApple OSS Distributions * This file contains Original Code and/or Modifications of Original Code 7*42e22086SApple OSS Distributions * as defined in and that are subject to the Apple Public Source License 8*42e22086SApple OSS Distributions * Version 2.0 (the 'License'). You may not use this file except in 9*42e22086SApple OSS Distributions * compliance with the License. The rights granted to you under the License 10*42e22086SApple OSS Distributions * may not be used to create, or enable the creation or redistribution of, 11*42e22086SApple OSS Distributions * unlawful or unlicensed copies of an Apple operating system, or to 12*42e22086SApple OSS Distributions * circumvent, violate, or enable the circumvention or violation of, any 13*42e22086SApple OSS Distributions * terms of an Apple operating system software license agreement. 14*42e22086SApple OSS Distributions * 15*42e22086SApple OSS Distributions * Please obtain a copy of the License at 16*42e22086SApple OSS Distributions * http://www.opensource.apple.com/apsl/ and read it before using this file. 17*42e22086SApple OSS Distributions * 18*42e22086SApple OSS Distributions * The Original Code and all software distributed under the License are 19*42e22086SApple OSS Distributions * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER 20*42e22086SApple OSS Distributions * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, 21*42e22086SApple OSS Distributions * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, 22*42e22086SApple OSS Distributions * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. 23*42e22086SApple OSS Distributions * Please see the License for the specific language governing rights and 24*42e22086SApple OSS Distributions * limitations under the License. 25*42e22086SApple OSS Distributions * 26*42e22086SApple OSS Distributions * @APPLE_OSREFERENCE_LICENSE_HEADER_END@ 27*42e22086SApple OSS Distributions */ 28*42e22086SApple OSS Distributions 29*42e22086SApple OSS Distributions #ifndef KPERF_KPTIMER_H 30*42e22086SApple OSS Distributions #define KPERF_KPTIMER_H 31*42e22086SApple OSS Distributions 32*42e22086SApple OSS Distributions /* 33*42e22086SApple OSS Distributions * kptimer is responsible for managing the kperf's on-CPU timers. These 34*42e22086SApple OSS Distributions * timers sample threads that are running on CPUs at a cadence determined by a 35*42e22086SApple OSS Distributions * specified period. When they fire, a handler runs the specified action and 36*42e22086SApple OSS Distributions * reprograms the timer to fire again. To get everything started or stopped, 37*42e22086SApple OSS Distributions * kptimer issues a broadcast IPI to modify kperf's multiplexed per-CPU timer, 38*42e22086SApple OSS Distributions * stored in the machine-dependent per-CPU structure. 39*42e22086SApple OSS Distributions * 40*42e22086SApple OSS Distributions * On-CPU timers are disabled when the CPU they've been programmed for goes idle 41*42e22086SApple OSS Distributions * to prevent waking up the idle CPU when it's not running anything interesting. 42*42e22086SApple OSS Distributions * This logic lives in the platform code that's responsible for entering and 43*42e22086SApple OSS Distributions * exiting idle. 44*42e22086SApple OSS Distributions * 45*42e22086SApple OSS Distributions * Traditional PET is configured here (since it's defined by identifying a timer 46*42e22086SApple OSS Distributions * to use for PET) but its mechanism is in osfmk/kperf/pet.c. Lightweight PET 47*42e22086SApple OSS Distributions * does use kptimer to increment its generation count, however. 48*42e22086SApple OSS Distributions */ 49*42e22086SApple OSS Distributions 50*42e22086SApple OSS Distributions /* 51*42e22086SApple OSS Distributions * The minimum allowed timer period depends on the type of client (foreground vs. 52*42e22086SApple OSS Distributions * background) and timer (on-CPU vs. PET). 53*42e22086SApple OSS Distributions */ 54*42e22086SApple OSS Distributions enum kptimer_period_limit { 55*42e22086SApple OSS Distributions KTPL_FG, 56*42e22086SApple OSS Distributions KTPL_BG, 57*42e22086SApple OSS Distributions KTPL_FG_PET, 58*42e22086SApple OSS Distributions KTPL_BG_PET, 59*42e22086SApple OSS Distributions KTPL_MAX, 60*42e22086SApple OSS Distributions }; 61*42e22086SApple OSS Distributions 62*42e22086SApple OSS Distributions /* 63*42e22086SApple OSS Distributions * The minimum timer periods allowed by kperf. There's no other mechanism 64*42e22086SApple OSS Distributions * to prevent interrupt storms due to kptimer. 65*42e22086SApple OSS Distributions */ 66*42e22086SApple OSS Distributions extern const uint64_t kptimer_minperiods_ns[KTPL_MAX]; 67*42e22086SApple OSS Distributions 68*42e22086SApple OSS Distributions /* 69*42e22086SApple OSS Distributions * Called from the kernel startup thread to set up kptimer. 70*42e22086SApple OSS Distributions */ 71*42e22086SApple OSS Distributions void kptimer_init(void); 72*42e22086SApple OSS Distributions 73*42e22086SApple OSS Distributions /* 74*42e22086SApple OSS Distributions * Return the minimum timer period in Mach time units. 75*42e22086SApple OSS Distributions */ 76*42e22086SApple OSS Distributions uint64_t kptimer_min_period_abs(bool pet); 77*42e22086SApple OSS Distributions 78*42e22086SApple OSS Distributions /* 79*42e22086SApple OSS Distributions * Return the number of timers available. 80*42e22086SApple OSS Distributions */ 81*42e22086SApple OSS Distributions unsigned int kptimer_get_count(void); 82*42e22086SApple OSS Distributions 83*42e22086SApple OSS Distributions /* 84*42e22086SApple OSS Distributions * Set the number of timers available to `count`. 85*42e22086SApple OSS Distributions * 86*42e22086SApple OSS Distributions * Returns 0 on success, and non-0 on error. 87*42e22086SApple OSS Distributions */ 88*42e22086SApple OSS Distributions int kptimer_set_count(unsigned int count); 89*42e22086SApple OSS Distributions 90*42e22086SApple OSS Distributions /* 91*42e22086SApple OSS Distributions * Return the period of the timer identified by `timerid` in `period_out`. 92*42e22086SApple OSS Distributions * 93*42e22086SApple OSS Distributions * Returns 0 on success, and non-0 on error. 94*42e22086SApple OSS Distributions */ 95*42e22086SApple OSS Distributions int kptimer_get_period(unsigned int timerid, uint64_t *period_out); 96*42e22086SApple OSS Distributions 97*42e22086SApple OSS Distributions /* 98*42e22086SApple OSS Distributions * Set the period of the timer identified by `timerid` to `period`. 99*42e22086SApple OSS Distributions * 100*42e22086SApple OSS Distributions * Returns non-zero on error, and zero otherwise. 101*42e22086SApple OSS Distributions */ 102*42e22086SApple OSS Distributions int kptimer_set_period(unsigned int timerid, uint64_t period); 103*42e22086SApple OSS Distributions 104*42e22086SApple OSS Distributions /* 105*42e22086SApple OSS Distributions * Return the action of the timer identified by `timerid` in 106*42e22086SApple OSS Distributions * `actionid_out`. 107*42e22086SApple OSS Distributions */ 108*42e22086SApple OSS Distributions int kptimer_get_action(unsigned int timerid, uint32_t *actionid_out); 109*42e22086SApple OSS Distributions 110*42e22086SApple OSS Distributions /* 111*42e22086SApple OSS Distributions * Set the action of the timer identified by `timerid` to `actionid`. 112*42e22086SApple OSS Distributions */ 113*42e22086SApple OSS Distributions int kptimer_set_action(unsigned int timer, uint32_t actionid); 114*42e22086SApple OSS Distributions 115*42e22086SApple OSS Distributions /* 116*42e22086SApple OSS Distributions * Set the PET timer to the timer identified by `timerid`. 117*42e22086SApple OSS Distributions */ 118*42e22086SApple OSS Distributions int kptimer_set_pet_timerid(unsigned int timerid); 119*42e22086SApple OSS Distributions 120*42e22086SApple OSS Distributions /* 121*42e22086SApple OSS Distributions * Return the ID of the PET timer. 122*42e22086SApple OSS Distributions */ 123*42e22086SApple OSS Distributions unsigned int kptimer_get_pet_timerid(void); 124*42e22086SApple OSS Distributions 125*42e22086SApple OSS Distributions /* 126*42e22086SApple OSS Distributions * For PET to rearm its timer after its sampling thread took `sampledur_abs` 127*42e22086SApple OSS Distributions * to sample. 128*42e22086SApple OSS Distributions */ 129*42e22086SApple OSS Distributions void kptimer_pet_enter(uint64_t sampledur_abs); 130*42e22086SApple OSS Distributions 131*42e22086SApple OSS Distributions /* 132*42e22086SApple OSS Distributions * Start all active timers. The ktrace lock must be held. 133*42e22086SApple OSS Distributions */ 134*42e22086SApple OSS Distributions void kptimer_start(void); 135*42e22086SApple OSS Distributions 136*42e22086SApple OSS Distributions /* 137*42e22086SApple OSS Distributions * Stop all active timers, waiting for them to stop. The ktrace lock must be held. 138*42e22086SApple OSS Distributions */ 139*42e22086SApple OSS Distributions void kptimer_stop(void); 140*42e22086SApple OSS Distributions 141*42e22086SApple OSS Distributions /* 142*42e22086SApple OSS Distributions * Cancel outstanding kperf timer for this CPU. 143*42e22086SApple OSS Distributions */ 144*42e22086SApple OSS Distributions void kptimer_stop_curcpu(void); 145*42e22086SApple OSS Distributions 146*42e22086SApple OSS Distributions /* 147*42e22086SApple OSS Distributions * Reconfigure this CPU's kptimer expiration when it's brought online 148*42e22086SApple OSS Distributions */ 149*42e22086SApple OSS Distributions void kptimer_curcpu_up(void); 150*42e22086SApple OSS Distributions 151*42e22086SApple OSS Distributions /* 152*42e22086SApple OSS Distributions * To indicate the next timer has expired. 153*42e22086SApple OSS Distributions */ 154*42e22086SApple OSS Distributions void kptimer_expire(processor_t processor, int cpuid, uint64_t now); 155*42e22086SApple OSS Distributions 156*42e22086SApple OSS Distributions /* 157*42e22086SApple OSS Distributions * Reset the kptimer system. 158*42e22086SApple OSS Distributions */ 159*42e22086SApple OSS Distributions void kptimer_reset(void); 160*42e22086SApple OSS Distributions 161*42e22086SApple OSS Distributions #endif /* !defined(KPERF_KPTIMER_H) */ 162