try_to_grab_pending(9)

πŸ“¦ version 7.3.1, in nixpkgs unstable

πŸ’… try_to_grab_pending(9) β€” Kernel API Manual ✨

okay so bestie, welcome to the Kernel API Manual page for try_to_grab_pending β€” she's a sneaky little function whose whole personality is stealing work items off the worklist and disabling irq. let's get into it πŸŽ€


🌸 NAME 🌸

try_to_grab_pending β€” steal work item from worklist and disable irq 🫢


✨ SYNOPSIS ✨

int try_to_grab_pending (struct work_struct *work , u32 cflags ,
       unsigned long *irq_flags );

πŸ¦‹ ARGUMENTS πŸ¦‹

  • work β€” the work item you're trying to steal, bestie. that's the target 🎯
  • cflags β€” the WORK_CANCEL_ flags, iykyk
  • irq_flags β€” the place where the irq state gets stored πŸ’Ύ

πŸ‘‘ DESCRIPTION πŸ‘‘

so the whole vibe is: try to grab the PENDING bit of work. this function is lowkey versatile β€” she can handle work in any stable state: idle, on timer, or on worklist. main character energy fr fr πŸ’…

here's what the return values mean, and yes we're keeping all of them:

  1. 1 β€” if work was pending and we successfully stole PENDING ✨
  2. 0 β€” if work was idle and we claimed PENDING
  3. -EAGAIN β€” if PENDING couldn't be grabbed at the moment, but it's safe to busy-retry πŸ”

πŸ’€ NOTE πŸ’€

listen up, this part matters 🚨

On a return value >= 0, the caller owns work's PENDING bit. and to avoid getting interrupted while holding PENDING with work off the queue, irq must be disabled on entry. this, combined with delayed_work->timer being irqsafe, is what ensures we return -EAGAIN for a finite short period of time. no cap 🧚

On a successful return β€” that's >= 0 β€” irq is disabled and the caller is responsible for releasing it using local_irq_restore(*irq_flags). don't forget, bestie, that's on you πŸ™ˆ

This function is safe to call from any context, including IRQ handler. literally anywhere, she doesn't care 🌈


πŸ”₯ SEE ALSO πŸ”₯

Kernel file ./kernel/workqueue.c β€” plus the whole extended friend group, and yes, we're listing every single one of them because everyone deserves their moment πŸ’–

for_each_pool(9), for_each_pool_worker(9), for_each_pwq(9), worker_pool_assign_id(9), unbound_effective_cpumask(9), get_work_pool(9), worker_set_flags(9), worker_clr_flags(9), worker_enter_idle(9), worker_leave_idle(9), find_worker_executing_work(9), move_linked_works(9), assign_work(9), kick_pool_pick(9), kick_pool(9), wq_worker_running(9), wq_worker_sleeping(9), wq_worker_tick(9), wq_worker_last_func(9), wq_node_nr_active(9), wq_update_node_max_active(9), get_pwq(9), put_pwq(9), put_pwq_unlocked(9), pwq_tryinc_nr_active(9), pwq_activate_first_inactive(9), unplug_oldest_pwq(9), node_activate_pending_pwq(9), pwq_dec_nr_active(9), pwq_dec_nr_in_flight(9), work_grab_pending(9), insert_work(9), queue_work_on(9), select_numa_node_cpu(9), queue_work_node(9), queue_delayed_work_on(9), mod_delayed_work_on(9), queue_rcu_work(9), worker_attach_to_pool(9), worker_detach_from_pool(9), create_worker(9), set_worker_dying(9), idle_worker_timeout(9), idle_cull_fn(9), maybe_create_worker(9), manage_workers(9), process_one_work(9), process_scheduled_works(9), worker_thread(9), rescuer_thread(9), check_flush_dependency(9), insert_wq_barrier(9), flush_workqueue_prep_pwqs(9), __flush_workqueue(9), drain_workqueue(9), flush_work(9), flush_delayed_work(9), flush_rcu_work(9), cancel_work_sync(9), cancel_delayed_work(9), cancel_delayed_work_sync(9), disable_work(9), disable_work_sync(9), enable_work(9), disable_delayed_work(9), disable_delayed_work_sync(9), enable_delayed_work(9), schedule_on_each_cpu(9), execute_in_process_context(9), free_workqueue_attrs(9), alloc_workqueue_attrs(9), init_worker_pool(9), put_unbound_pool(9), get_unbound_pool(9), wq_calc_pod_cpumask(9), apply_workqueue_attrs(9), unbound_wq_update_pwq(9), wq_adjust_max_active(9), destroy_workqueue(9), workqueue_set_max_active(9), workqueue_set_min_active(9), current_work(9), current_is_workqueue_rescuer(9), current_is_workqueue_mem_reclaim(9), workqueue_congested(9), work_busy(9), set_worker_desc(9), print_worker_info(9), show_one_workqueue(9), show_one_worker_pool(9), show_all_workqueues(9), show_freezable_workqueues(9), rebind_workers(9), restore_unbound_workers_cpumask(9), work_on_cpu_key(9), freeze_workqueues_begin(9), freeze_workqueues_busy(9), thaw_workqueues(9), workqueue_unbound_housekeeping_update(9), workqueue_set_unbound_cpumask(9), workqueue_sysfs_register(9), workqueue_sysfs_unregister(9), workqueue_init_early(9), workqueue_init(9), llc_count_cores(9), llc_populate_cpu_shard_id(9), precompute_cache_shard_ids(9), workqueue_init_topology(9)


okay that's the whole page, you ate that πŸ’…βœ¨

and a lil sign-off from your girl: this one's from <lavender>./kernel</lavender>, dated October 2026, page version try_to_grab_pending(9). drink some water, go touch grass, and remember to local_irq_restore πŸ“πŸ«Ά

πŸ“¦ where this page comes from