-
Notifications
You must be signed in to change notification settings - Fork 0
DeviceException DriverException
Base exception hierarchy for JNode's device and driver framework, with subclasses covering registration, lookup, API access, and binding errors.
JNode's device framework uses two parallel checked exception hierarchies to separate device-level errors from driver-level errors. Both extend java.lang.Exception and live in org.jnode.driver.
DeviceException covers errors in the device lifecycle: registration in the DeviceManager, lookup by ID, and API access via Device.getAPI(). Its subclasses represent problems with the device registry or device state.
DriverException covers errors in the driver lifecycle: connecting a driver to a device, starting/stopping devices, and claiming hardware resources (IRQ, I/O ports, memory). Its subclasses represent problems with the driver-device binding mechanism.
The exception hierarchy is:
Exception
├── DeviceException (device-level errors)
│ ├── ApiNotFoundException (API not registered on device)
│ ├── DeviceAlreadyRegisteredException (device already in DeviceManager)
│ ├── DeviceNotFoundException (device ID not found in DeviceManager)
│ └── ChannelAlreadyOwnedException (character channel already claimed)
│
└── DriverException (driver-level errors)
├── DeviceAlreadyConnectedException (driver already bound to a device)
└── InvalidDriverException (driver not valid for a device)
All exceptions except ChannelAlreadyOwnedException follow the standard four-constructor pattern (no-arg, message, cause, message+cause) and were authored by Ewout Prangsma.
| Class | Path | Role |
|---|---|---|
DeviceException |
core/src/driver/org/jnode/driver/DeviceException.java |
Base exception for device-level errors (registration, lookup, API) |
DriverException |
core/src/driver/org/jnode/driver/DriverException.java |
Base exception for driver-level errors (connection, resource claiming) |
ApiNotFoundException |
core/src/driver/org/jnode/driver/ApiNotFoundException.java |
Thrown by Device.getAPI() when requested interface is not registered |
DeviceAlreadyRegisteredException |
core/src/driver/org/jnode/driver/DeviceAlreadyRegisteredException.java |
Thrown by AbstractDeviceManager.register() for duplicate device IDs |
DeviceNotFoundException |
core/src/driver/org/jnode/driver/DeviceNotFoundException.java |
Thrown by AbstractDeviceManager.getDevice() when device ID not found |
ChannelAlreadyOwnedException |
core/src/driver/org/jnode/driver/character/ChannelAlreadyOwnedException.java |
Thrown when a character device channel is already claimed by another device |
DeviceAlreadyConnectedException |
core/src/driver/org/jnode/driver/DeviceAlreadyConnectedException.java |
Thrown when a driver is already connected to a device |
InvalidDriverException |
core/src/driver/org/jnode/driver/InvalidDriverException.java |
Thrown by ByteArrayDevice.setDriver() to reject driver assignment |
DeviceException and its subclasses are thrown during the device registration and lookup lifecycle:
DeviceManager.register(device)
└── throws DeviceAlreadyRegisteredException (device ID already in registry)
DeviceManager.getDevice(id)
└── throws DeviceNotFoundException (no device with that ID)
Device.getAPI(SomeAPI.class)
└── throws ApiNotFoundException (API not registered on device)
SerialPortDriver / PS2Driver
└── throws ChannelAlreadyOwnedException (character channel already claimed)
The most-caught subclass is ApiNotFoundException (52 catch sites), because Device.getAPI() is the primary way code accesses device functionality. The typical pattern is:
try {
SomeAPI api = device.getAPI(SomeAPI.class);
// use api
} catch (ApiNotFoundException e) {
// fallback or log
}DeviceAlreadyRegisteredException (29 catch sites) is commonly caught during startDevice() when registering child devices (e.g., PCI driver registering sub-devices), since duplicate registration is a common race condition.
DriverException is the "workhorse" exception with ~181 throw sites across the codebase. It is the standard way to signal failure during driver startDevice() operations:
Driver.connect(device)
└── throws DriverException("This driver is already connected to a device")
Device.setDriver(driver)
└── wraps DriverException("Cannot set driver")
Device.start()
└── throws DriverException("Cannot start without a driver")
throws DriverException("Cannot start without being registered")
Device.stop()
└── throws DriverException("Cannot stop without a driver")
throws DriverException("Cannot stop without being registered")
Common DriverException message patterns across drivers:
| Message Pattern | Context | Frequency |
|---|---|---|
| "Cannot find ResourceManager" | JNDI lookup for ResourceManager.NAME fails |
Most common |
| "Cannot claim {resource} resources" | Resource contention (IRQ, I/O ports) | ~30 sites |
| "Cannot find DeviceManager" | JNDI lookup failure | ~10 sites |
| "Timeout in {command} command" | Hardware command timeouts (e.g., Prism2 WiFi) | ~15 sites |
| "Card failure" / "No buffer" | Hardware state errors | ~10 sites |
| "Unknown exception" | Catch-all wrapping unexpected throwables | ~20 sites |
DriverException is heavily concentrated in net drivers (~80+ throw sites across RTL8139, Prism2, Ne2000, EEPRO100, BCM570x, etc.), gui drivers (~20 sites), and fs drivers (~15 sites).
Boot → DeviceFinder discovers hardware
→ DeviceManager.register(device)
└── DeviceAlreadyRegisteredException if duplicate
Plugin loads driver
→ Driver.connect(device)
└── DriverException if already connected
→ Device.setDriver(driver)
└── DriverException("Cannot set driver") wraps connect failure
→ Device.start()
└── DriverException if no driver or not registered
└── DriverException("Cannot claim IRQ") on resource conflict
Runtime: device.getAPI(SomeAPI.class)
└── ApiNotFoundException if API not registered
-
DeviceAlreadyConnectedException is never directly thrown: Despite having its own class,
Driver.connect()throws a plainDriverException("This driver is already connected to a device")rather than this subclass. The class exists as a semantic marker but is not used in practice. -
InvalidDriverException is never caught: It is thrown only by
ByteArrayDevice.setDriver()as a rejection mechanism ("No driver allowed here"), and no code catches it specifically. -
ChannelAlreadyOwnedException is the odd one out: It lives in a different package (
org.jnode.driver.character), has a custom single-arg constructor taking aDevice(not the standard four-constructor pattern), and is authored by "qades" rather than Ewout Prangsma. It is only thrown in two places (serial and PS2 drivers). -
ApiNotFoundException is the most-caught subclass (52 catch sites): This is because
Device.getAPI()is the primary way code accesses device functionality. If you are writing device-aware code, you must handle this exception. - DeviceException vs DriverException boundary: DeviceException covers the device side (registration, lookup, API access), while DriverException covers the driver side (connection, starting, stopping, resource claiming). This is a clean conceptual boundary that guides which exception to throw.
-
Both are checked exceptions: Both extend
java.lang.Exceptiondirectly, so all throw sites must declarethrowsor wrap in a runtime exception.
- Driver-Framework — Hub page for the device/driver model
- Device-Manager — Central device registry where DeviceAlreadyRegisteredException and DeviceNotFoundException are thrown
- DeviceAPI — Device API pattern where ApiNotFoundException is thrown
- DeviceAlreadyConnectedException — Dedicated page for the unused DriverException subclass
- Resource-Management — Where resource-claiming DriverExceptions originate
- DeviceToDriverMapper — Driver matching where InvalidDriverException may be relevant
- DeviceFinder — Device discovery where DeviceNotFoundException may occur