Skip to content

Driver I/O Model (Blocking / Non-blocking / poll)

🧠 Overview

Linux driver data path is event-driven, not polling-driven.

Core idea:

IRQ → event queue → wake_up() → user-space read/poll


🔁 Blocking vs Non-blocking

Blocking I/O

  • read() will sleep if no data
  • process is put into wait queue
  • resumed when data arrives

Typical pattern:

if (!data_available) {
    wait_event_interruptible(queue, condition);
}

Non-blocking I/O

  • controlled by file flag: O_NONBLOCK
  • read() returns immediately
if (!data_available) {
    if (file->f_flags & O_NONBLOCK)
        return -EAGAIN;
}

💤 Wait Queue

Purpose

  • bridge between:
  • interrupt context
  • process context

Key APIs

wait_event_interruptible(queue, condition);
wake_up_interruptible(&queue);

Behavior

  1. process calls read()
  2. no data → sleep
  3. IRQ occurs
  4. driver calls wake_up()
  5. process resumes

📡 poll / select / epoll

Role

Allow user-space to wait for events without blocking read()

Driver side

poll_wait(file, &dev->read_queue, wait);

if (data_available)
    return POLLIN;

User side

poll(fds, nfds, timeout);

🔄 Event Flow (Driver)

IRQ
 → schedule_work / delayed_work
 → read GPIO
 → detect state change
 → enqueue event
 → wake_up_interruptible()

📦 Event Queue Design

Why needed?

  • decouple IRQ and user-space
  • avoid losing events
  • support burst events

Implementation

  • ring buffer
  • protected by spinlock
enqueue()  // ISR or workqueue
dequeue()  // read()

🔐 Locking Strategy

Resource Lock
event queue spinlock
control params mutex

⚠️ Common Pitfalls

1. Fake blocking

❌ busy loop in read()
✔ must use wait_event


2. Missing wake_up()

→ read() never returns


3. Wake without condition

→ spurious wakeup (acceptable but noisy)


4. Race condition

check + dequeue not atomic

(acceptable in simple driver)


🎯 Key Takeaway

A correct Linux driver must:

  • sleep when no data
  • wake on event
  • never busy loop
  • support poll()

This is the standard I/O model used by:

  • UART
  • input subsystem
  • network stack
  • sensors