@ -60,6 +60,7 @@ struct ll_queue* queue_new(struct UASYNC* ua, size_t hash_size, uint16_t index_o
q - > size_limit = - 1 ; // Без ограничения по умолчанию
q - > threshold_max_packets = 0 ; // По умолчанию: ждать пустой очереди
q - > threshold_max_bytes = 0 ; // По умолчанию: не проверять байты
q - > waiter_defer = 0 ;
q - > hash_size = hash_size ;
q - > index_offset = index_offset ;
q - > index_size = index_size ;
@ -277,6 +278,21 @@ static uint32_t make_hash(const void* data, uint16_t len) {// алгоритм F
return hash ;
}
static void waiter_defer_cb ( void * arg ) {
struct queue_waiter_handle * h = ( struct queue_waiter_handle * ) arg ;
h - > defer_cb ( h - > defer_q , h - > defer_arg ) ;
}
inline void queue_waiter_call ( struct ll_queue * q , queue_threshold_callback_fn cb , void * arg ,
struct queue_waiter_handle * h ) {
if ( q - > waiter_defer ) {
h - > defer_q = q ; h - > defer_cb = cb ; h - > defer_arg = arg ;
uasync_call_soon ( q - > ua , h , waiter_defer_cb ) ;
} else {
cb ( q , arg ) ;
}
}
// Проверить и запустить первый ожидающий коллбэк (FIFO / round-robin)
static void check_waiters ( struct ll_queue * q ) {
if ( ! q | | ! q - > waiter_head ) return ;
@ -299,7 +315,7 @@ static void check_waiters(struct ll_queue* q) {
if ( cb ) {
DEBUG_DEBUG ( DEBUG_CATEGORY_LL_QUEUE , " check_waiters: waking head waiter, count=%d<=%d, bytes=%zu<=%zu " ,
q - > count , q - > threshold_max_packets , q - > total_bytes , q - > threshold_max_bytes ) ;
cb ( q , arg ) ;
queue_waiter_call ( q , cb , arg , h ) ;
}
}
@ -592,6 +608,11 @@ void queue_set_threshold(struct ll_queue* q, int max_packets, size_t max_bytes)
q - > threshold_max_bytes = max_bytes ;
}
void queue_set_waiter_defer ( struct ll_queue * q , int enable ) {
if ( ! q ) return ;
q - > waiter_defer = enable ;
}
int queue_waiter_wait ( struct ll_queue * q , struct queue_waiter_handle * h ,
queue_threshold_callback_fn callback , void * arg ) {
if ( ! q | | ! h ) return - 1 ;
@ -600,7 +621,7 @@ int queue_waiter_wait(struct ll_queue* q, struct queue_waiter_handle* h,
if ( q - > count < = q - > threshold_max_packets
& & ( q - > threshold_max_bytes = = 0 | | q - > total_bytes < = q - > threshold_max_bytes ) ) {
callback ( q , arg ) ;
queue_waiter_ call( q , callback , arg , h ) ;
return 1 ;
}