drivers/input/keyboard/ep93xx_keypad.c
Source file repositories/reference/linux-study-clean/drivers/input/keyboard/ep93xx_keypad.c
File Facts
- System
- Linux kernel
- Corpus path
drivers/input/keyboard/ep93xx_keypad.c- Extension
.c- Size
- 7456 bytes
- Lines
- 296
- Domain
- Driver Families
- Bucket
- drivers/input
- Inferred role
- Driver Families: implementation source
- Status
- source implementation candidate
Why This File Exists
Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Touches IRQ or DMA behavior; this matters for the representative real-device path.
- Allocates kernel memory; connect allocation flags and lifetime to context constraints.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/bits.hlinux/mod_devicetable.hlinux/module.hlinux/platform_device.hlinux/property.hlinux/interrupt.hlinux/clk.hlinux/io.hlinux/input.hlinux/input/matrix_keypad.hlinux/slab.hlinux/soc/cirrus/ep93xx.hlinux/pm_wakeirq.h
Detected Declarations
struct ep93xx_keypadfunction ep93xx_keypad_irq_handlerfunction ep93xx_keypad_configfunction ep93xx_keypad_openfunction ep93xx_keypad_closefunction ep93xx_keypad_suspendfunction ep93xx_keypad_resumefunction ep93xx_keypad_probefunction ep93xx_keypad_remove
Annotated Snippet
struct ep93xx_keypad {
struct input_dev *input_dev;
struct clk *clk;
unsigned int debounce;
u16 prescale;
void __iomem *mmio_base;
unsigned short keycodes[EP93XX_MATRIX_SIZE];
int key1;
int key2;
int irq;
bool enabled;
};
static irqreturn_t ep93xx_keypad_irq_handler(int irq, void *dev_id)
{
struct ep93xx_keypad *keypad = dev_id;
struct input_dev *input_dev = keypad->input_dev;
unsigned int status;
int keycode, key1, key2;
status = __raw_readl(keypad->mmio_base + KEY_REG);
keycode = (status & KEY_REG_KEY1_MASK) >> KEY_REG_KEY1_SHIFT;
key1 = keypad->keycodes[keycode];
keycode = (status & KEY_REG_KEY2_MASK) >> KEY_REG_KEY2_SHIFT;
key2 = keypad->keycodes[keycode];
if (status & KEY_REG_2KEYS) {
if (keypad->key1 && key1 != keypad->key1 && key2 != keypad->key1)
input_report_key(input_dev, keypad->key1, 0);
if (keypad->key2 && key1 != keypad->key2 && key2 != keypad->key2)
input_report_key(input_dev, keypad->key2, 0);
input_report_key(input_dev, key1, 1);
input_report_key(input_dev, key2, 1);
keypad->key1 = key1;
keypad->key2 = key2;
} else if (status & KEY_REG_1KEY) {
if (keypad->key1 && key1 != keypad->key1)
input_report_key(input_dev, keypad->key1, 0);
if (keypad->key2 && key1 != keypad->key2)
input_report_key(input_dev, keypad->key2, 0);
input_report_key(input_dev, key1, 1);
keypad->key1 = key1;
keypad->key2 = 0;
} else {
input_report_key(input_dev, keypad->key1, 0);
input_report_key(input_dev, keypad->key2, 0);
keypad->key1 = keypad->key2 = 0;
}
input_sync(input_dev);
return IRQ_HANDLED;
}
static void ep93xx_keypad_config(struct ep93xx_keypad *keypad)
{
unsigned int val = 0;
val |= (keypad->debounce << KEY_INIT_DBNC_SHIFT) & KEY_INIT_DBNC_MASK;
val |= (keypad->prescale << KEY_INIT_PRSCL_SHIFT) & KEY_INIT_PRSCL_MASK;
__raw_writel(val, keypad->mmio_base + KEY_INIT);
}
static int ep93xx_keypad_open(struct input_dev *pdev)
{
struct ep93xx_keypad *keypad = input_get_drvdata(pdev);
if (!keypad->enabled) {
ep93xx_keypad_config(keypad);
clk_prepare_enable(keypad->clk);
keypad->enabled = true;
}
Annotation
- Immediate include surface: `linux/bits.h`, `linux/mod_devicetable.h`, `linux/module.h`, `linux/platform_device.h`, `linux/property.h`, `linux/interrupt.h`, `linux/clk.h`, `linux/io.h`.
- Detected declarations: `struct ep93xx_keypad`, `function ep93xx_keypad_irq_handler`, `function ep93xx_keypad_config`, `function ep93xx_keypad_open`, `function ep93xx_keypad_close`, `function ep93xx_keypad_suspend`, `function ep93xx_keypad_resume`, `function ep93xx_keypad_probe`, `function ep93xx_keypad_remove`.
- Atlas domain: Driver Families / drivers/input.
- Implementation status: source implementation candidate.
- IRQ or DMA behavior appears here, which is relevant to the selected PCIe/NVMe device path.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.