1. Linux 红外发送驱动架构解析
在Linux内核中,红外发送功能的实现涉及多个子系统的协同工作。让我们先了解整体架构:
核心组件关系图:
code复制用户空间应用程序
↓
/dev/lirc0 (字符设备接口)
↓
lirc_dev (LIRC设备框架)
↓
rc-core (红外核心子系统)
↓
pwm-ir-tx (具体硬件驱动)
↓
PWM控制器硬件
这个架构体现了Linux设备驱动的典型分层设计思想。用户空间通过标准的字符设备接口与内核交互,而内核则通过抽象层将具体硬件实现细节隔离。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. PWM红外发送驱动初始化流程
2.1 设备树匹配与驱动注册
驱动初始化的起点是设备树匹配。在设备树中,我们需要定义PWM红外发送节点:
dts复制pwm_ir: pwm-ir {
compatible = "pwm-ir-tx";
pwms = <&pwm 0 26316>; // 38kHz PWM
duty-cycle = <13158>; // 50% duty
};
驱动通过of_match_table进行匹配:
c复制static const struct of_device_id pwm_ir_of_match[] = {
{ .compatible = "pwm-ir-tx", },
{ },
};
MODULE_DEVICE_TABLE(of, pwm_ir_of_match);
提示:设备树中的
compatible字符串必须与驱动中定义的一致,否则无法匹配成功。
2.2 probe函数详细解析
pwm_ir_probe()是驱动初始化的核心函数,其执行流程如下:
- 资源分配:
c复制struct pwm_ir *pwm_ir = devm_kmalloc(dev, sizeof(*pwm_ir), GFP_KERNEL);
- PWM控制器获取:
c复制pwm_ir->pwm = devm_pwm_get(dev, NULL);
if (IS_ERR(pwm_ir->pwm)) {
dev_err(dev, "Failed to get PWM\n");
return PTR_ERR(pwm_ir->pwm);
}
- 默认参数设置:
c复制pwm_ir->carrier = 38000; // 38kHz载波
pwm_ir->duty_cycle = 50; // 50%占空比
- RC设备分配与注册:
c复制rcdev = devm_rc_allocate_device(dev, RC_DRIVER_IR_RAW_TX);
rcdev->priv = pwm_ir;
rcdev->tx_ir = pwm_ir_tx;
rcdev->s_tx_carrier = pwm_ir_set_carrier;
rcdev->s_tx_duty_cycle = pwm
