123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136 |
- rfkill - RF kill switch support
- ===============================
- 1. Introduction
- 2. Implementation details
- 3. Kernel driver guidelines
- 4. Kernel API
- 5. Userspace support
- 1. Introduction
- The rfkill subsystem provides a generic interface to disabling any radio
- transmitter in the system. When a transmitter is blocked, it shall not
- radiate any power.
- The subsystem also provides the ability to react on button presses and
- disable all transmitters of a certain type (or all). This is intended for
- situations where transmitters need to be turned off, for example on
- aircraft.
- 2. Implementation details
- The rfkill subsystem is composed of various components: the rfkill class, the
- rfkill-input module (an input layer handler), and some specific input layer
- events.
- The rfkill class is provided for kernel drivers to register their radio
- transmitter with the kernel, provide methods for turning it on and off and,
- optionally, letting the system know about hardware-disabled states that may
- be implemented on the device. This code is enabled with the CONFIG_RFKILL
- Kconfig option, which drivers can "select".
- The rfkill class code also notifies userspace of state changes, this is
- achieved via uevents. It also provides some sysfs files for userspace to
- check the status of radio transmitters. See the "Userspace support" section
- below.
- The rfkill-input code implements a basic response to rfkill buttons -- it
- implements turning on/off all devices of a certain class (or all).
- When the device is hard-blocked (either by a call to rfkill_set_hw_state()
- or from query_hw_block) set_block() will be invoked but drivers can well
- ignore the method call since they can use the return value of the function
- rfkill_set_hw_state() to sync the software state instead of keeping track
- of calls to set_block().
- The entire functionality is spread over more than one subsystem:
- * The kernel input layer generates KEY_WWAN, KEY_WLAN etc. and
- SW_RFKILL_ALL -- when the user presses a button. Drivers for radio
- transmitters generally do not register to the input layer, unless the
- device really provides an input device (i.e. a button that has no
- effect other than generating a button press event)
- * The rfkill-input code hooks up to these events and switches the soft-block
- of the various radio transmitters, depending on the button type.
- * The rfkill drivers turn off/on their transmitters as requested.
- * The rfkill class will generate userspace notifications (uevents) to tell
- userspace what the current state is.
- 3. Kernel driver guidelines
- Drivers for radio transmitters normally implement only the rfkill class.
- These drivers may not unblock the transmitter based on own decisions, they
- should act on information provided by the rfkill class only.
- Platform drivers might implement input devices if the rfkill button is just
- that, a button. If that button influences the hardware then you need to
- implement an rfkill class instead. This also applies if the platform provides
- a way to turn on/off the transmitter(s).
- During suspend/hibernation, transmitters should only be left enabled when
- wake-on wlan or similar functionality requires it and the device wasn't
- blocked before suspend/hibernate. Note that it may be necessary to update
- the rfkill subsystem's idea of what the current state is at resume time if
- the state may have changed over suspend.
- 4. Kernel API
- To build a driver with rfkill subsystem support, the driver should depend on
- (or select) the Kconfig symbol RFKILL.
- The hardware the driver talks to may be write-only (where the current state
- of the hardware is unknown), or read-write (where the hardware can be queried
- about its current state).
- Calling rfkill_set_hw_state() when a state change happens is required from
- rfkill drivers that control devices that can be hard-blocked unless they also
- assign the poll_hw_block() callback (then the rfkill core will poll the
- device). Don't do this unless you cannot get the event in any other way.
- 5. Userspace support
- The following sysfs entries exist for every rfkill device:
- name: Name assigned by driver to this key (interface or driver name).
- type: Name of the key type ("wlan", "bluetooth", etc).
- state: Current state of the transmitter
- 0: RFKILL_STATE_SOFT_BLOCKED
- transmitter is turned off by software
- 1: RFKILL_STATE_UNBLOCKED
- transmitter is (potentially) active
- 2: RFKILL_STATE_HARD_BLOCKED
- transmitter is forced off by something outside of
- the driver's control.
- claim: 0: Kernel handles events (currently always reads that value)
- rfkill devices also issue uevents (with an action of "change"), with the
- following environment variables set:
- RFKILL_NAME
- RFKILL_STATE
- RFKILL_TYPE
- The contents of these variables corresponds to the "name", "state" and
- "type" sysfs files explained above.
- An alternative userspace interface exists as a misc device /dev/rfkill,
- which allows userspace to obtain and set the state of rfkill devices and
- sets of devices. It also notifies userspace about device addition and
- removal. The API is a simple read/write API that is defined in
- linux/rfkill.h.
|