194a2ceb1SMichal Wajdeczko /* SPDX-License-Identifier: MIT */ 294a2ceb1SMichal Wajdeczko /* 394a2ceb1SMichal Wajdeczko * Copyright © 2026 Intel Corporation 494a2ceb1SMichal Wajdeczko */ 594a2ceb1SMichal Wajdeczko 694a2ceb1SMichal Wajdeczko #ifndef _XE_SLEEP_H_ 794a2ceb1SMichal Wajdeczko #define _XE_SLEEP_H_ 894a2ceb1SMichal Wajdeczko 994a2ceb1SMichal Wajdeczko #include <linux/delay.h> 1094a2ceb1SMichal Wajdeczko #include <linux/math64.h> 1194a2ceb1SMichal Wajdeczko 1294a2ceb1SMichal Wajdeczko /** 1394a2ceb1SMichal Wajdeczko * xe_sleep_relaxed_ms() - Sleep for an approximate time. 1494a2ceb1SMichal Wajdeczko * @delay_ms: time in msec to sleep 1594a2ceb1SMichal Wajdeczko * 1694a2ceb1SMichal Wajdeczko * For smaller timeouts, sleep with 0.5ms accuracy. 1794a2ceb1SMichal Wajdeczko */ 1894a2ceb1SMichal Wajdeczko static inline void xe_sleep_relaxed_ms(unsigned int delay_ms) 1994a2ceb1SMichal Wajdeczko { 2094a2ceb1SMichal Wajdeczko unsigned long min_us, max_us; 2194a2ceb1SMichal Wajdeczko 2294a2ceb1SMichal Wajdeczko if (!delay_ms) 2394a2ceb1SMichal Wajdeczko return; 2494a2ceb1SMichal Wajdeczko 2594a2ceb1SMichal Wajdeczko if (delay_ms > 20) { 2694a2ceb1SMichal Wajdeczko msleep(delay_ms); 2794a2ceb1SMichal Wajdeczko return; 2894a2ceb1SMichal Wajdeczko } 2994a2ceb1SMichal Wajdeczko 3094a2ceb1SMichal Wajdeczko min_us = mul_u32_u32(delay_ms, 1000); 3194a2ceb1SMichal Wajdeczko max_us = min_us + 500; 3294a2ceb1SMichal Wajdeczko 3394a2ceb1SMichal Wajdeczko usleep_range(min_us, max_us); 3494a2ceb1SMichal Wajdeczko } 3594a2ceb1SMichal Wajdeczko 36*eec43f36SMichal Wajdeczko /** 37*eec43f36SMichal Wajdeczko * xe_sleep_exponential_ms() - Sleep for a exponentially increased time. 38*eec43f36SMichal Wajdeczko * @sleep_period_ms: current time in msec to sleep 39*eec43f36SMichal Wajdeczko * @max_sleep_ms: maximum time in msec to sleep 40*eec43f36SMichal Wajdeczko * 41*eec43f36SMichal Wajdeczko * Sleep for the @sleep_period_ms and exponentially increase this time for the 42*eec43f36SMichal Wajdeczko * next loop, unless reaching the @max_sleep_ms limit. 43*eec43f36SMichal Wajdeczko * 44*eec43f36SMichal Wajdeczko * Return: approximate time in msec the task was delayed. 45*eec43f36SMichal Wajdeczko */ 46*eec43f36SMichal Wajdeczko static inline unsigned int xe_sleep_exponential_ms(unsigned int *sleep_period_ms, 47*eec43f36SMichal Wajdeczko unsigned int max_sleep_ms) 48*eec43f36SMichal Wajdeczko { 49*eec43f36SMichal Wajdeczko unsigned int delay_ms = *sleep_period_ms; 50*eec43f36SMichal Wajdeczko unsigned int next_delay_ms = 2 * delay_ms; 51*eec43f36SMichal Wajdeczko 52*eec43f36SMichal Wajdeczko xe_sleep_relaxed_ms(delay_ms); 53*eec43f36SMichal Wajdeczko *sleep_period_ms = min(next_delay_ms, max_sleep_ms); 54*eec43f36SMichal Wajdeczko return delay_ms; 55*eec43f36SMichal Wajdeczko } 56*eec43f36SMichal Wajdeczko 5794a2ceb1SMichal Wajdeczko #endif 58