Linux内核 -- RTC 驱动的注册方式

Linux 内核中 RTC 驱动的注册方式

在 Linux 内核中,RTC(Real-Time Clock)驱动的注册可以通过多种方式实现,以下整理了常见的注册方式及其注意事项。

1. 使用 devm_rtc_device_register

这是注册 RTC 驱动的最常用方法,基于设备资源管理(devm_)机制,能够自动管理资源释放。

示例代码

#include <linux/rtc.h>static int rtc_read_time(struct device *dev, struct rtc_time *tm) {// 模拟读取时间tm->tm_sec = 30;tm->tm_min = 15;tm->tm_hour = 10;tm->tm_mday = 25;tm->tm_mon = 5;tm->tm_year = 123; // 表示 2023 年return 0;
}static int rtc_set_time(struct device *dev, struct rtc_time *tm) {// 模拟设置时间pr_info("Setting time: %d:%d:%d\n", tm->tm_hour, tm->tm_min, tm->tm_sec);return 0;
}static const struct rtc_class_ops rtc_ops = {.read_time = rtc_read_time,.set_time = rtc_set_time,
};static int rtc_probe(struct platform_device *pdev) {struct rtc_device *rtc;rtc = devm_rtc_device_register(&pdev->dev, "rtc-name", &rtc_ops, THIS_MODULE);if (IS_ERR(rtc))return PTR_ERR(rtc);return 0;
}

适用场景

  • 驱动逻辑较简单。
  • 希望简化资源管理工作。

注意事项

  • 必须确保设备正确传递到 devm_ 机制中。
  • 如果需要手动释放资源,请使用 rtc_device_register

2. 使用 rtc_device_register

相比 devm_rtc_device_register,此方法需要手动管理资源,适用于需要更高资源控制的场景。

示例代码

#include <linux/rtc.h>static int rtc_read_time(struct device *dev, struct rtc_time *tm) {// 模拟读取时间tm->tm_sec = 30;tm->tm_min = 15;tm->tm_hour = 10;tm->tm_mday = 25;tm->tm_mon = 5;tm->tm_year = 123; // 表示 2023 年return 0;
}static int rtc_set_time(struct device *dev, struct rtc_time *tm) {// 模拟设置时间pr_info("Setting time: %d:%d:%d\n", tm->tm_hour, tm->tm_min, tm->tm_sec);return 0;
}static const struct rtc_class_ops rtc_ops = {.read_time = rtc_read_time,.set_time = rtc_set_time,
};struct rtc_device *rtc;rtc = rtc_device_register("rtc-name", dev, &rtc_ops, THIS_MODULE);
if (IS_ERR(rtc))return PTR_ERR(rtc);/* 在 remove 或出错路径中释放资源 */
rtc_device_unregister(rtc);

适用场景

  • 驱动需要复杂的初始化逻辑。
  • 不希望依赖 devm_ 机制。

注意事项

  • 在驱动卸载时需手动调用 rtc_device_unregister 释放资源。
  • 避免资源泄漏。

3. 通过设备树或 ACPI 自动绑定

当 RTC 设备通过设备树或 ACPI 描述时,可以自动绑定到对应的驱动。

示例设备树

rtc@10000000 {compatible = "vendor,rtc";reg = <0x10000000 0x100>;
};

示例驱动代码

static int rtc_read_time(struct device *dev, struct rtc_time *tm) {// 模拟读取时间tm->tm_sec = 30;tm->tm_min = 15;tm->tm_hour = 10;tm->tm_mday = 25;tm->tm_mon = 5;tm->tm_year = 123; // 表示 2023 年return 0;
}static int rtc_set_time(struct device *dev, struct rtc_time *tm) {// 模拟设置时间pr_info("Setting time: %d:%d:%d\n", tm->tm_hour, tm->tm_min, tm->tm_sec);return 0;
}static const struct rtc_class_ops rtc_ops = {.read_time = rtc_read_time,.set_time = rtc_set_time,
};static int rtc_probe(struct platform_device *pdev) {struct rtc_device *rtc;rtc = devm_rtc_device_register(&pdev->dev, "rtc-name", &rtc_ops, THIS_MODULE);if (IS_ERR(rtc))return PTR_ERR(rtc);return 0;
}

适用场景

  • 嵌入式系统中常见。
  • RTC 资源通过设备树或 ACPI 描述。

注意事项

  • 确保 compatible 字段与驱动匹配。
  • 驱动需正确处理资源获取和释放。

4. 使用 rtc_class

适用于创建自定义 RTC 类设备的场景。

示例代码

#include <linux/rtc.h>
#include <linux/device.h>struct class *rtc_class;
struct device *rtc_dev;rtc_class = class_create(THIS_MODULE, "rtc");
if (IS_ERR(rtc_class))return PTR_ERR(rtc_class);rtc_dev = device_create(rtc_class, NULL, MKDEV(0, 0), NULL, "rtc0");
if (IS_ERR(rtc_dev)) {class_destroy(rtc_class);return PTR_ERR(rtc_dev);
}/* 在退出时清理资源 */
device_destroy(rtc_class, MKDEV(0, 0));
class_destroy(rtc_class);

适用场景

  • 自定义 RTC 类设备。
  • 需要特殊行为的 RTC 设备。

注意事项

  • 必须手动管理资源,避免资源泄漏。
  • 需要显式调用 class_destroydevice_destroy

注意事项

  1. 选择合适的注册方式

    • 简单驱动可用 devm_rtc_device_register
    • 需要手动控制资源时选择 rtc_device_register
    • 测试或模拟设备时使用设备树或 ACPI 自动绑定。
  2. 设备树支持:确保设备树描述与驱动匹配。

  3. 资源管理

    • 使用 devm_ 接口时资源自动管理。
    • 手动注册时注意清理资源。
  4. 兼容性

    • 检查硬件是否支持 RTC。
    • 根据具体硬件接口(I2C、SPI、平台设备)选择正确的实现方式。
  5. 功能扩展:可根据需求增加闹钟功能、中断支持等。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/bicheng/66453.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

JavaEE初阶——计算机工作原理

一、什么是JavaEE JavaEE&#xff08;Java Platform&#xff0c;Enterprise Edition&#xff09;是sun公司&#xff08;2009年4月20日甲骨文将其收购&#xff09;推出的企业级应用程序版本。这个版本以前称为 J2EE。能够帮助我们开发和部署可移植、健壮、可伸缩且安全的服务器…

多目标优化算法——基于聚类的不规则Pareto前沿多目标优化自适应进化算法(CA-MOEA)

基于聚类的不规则Pareto前沿多目标优化自适应进化算法&#xff08;CA-MOEA&#xff09; 一、算法简介 简介&#xff1a; 现有的多目标进化算法&#xff08;moea&#xff09;在具有规则Pareto前沿且Pareto最优解在目标空间上连续分布的多目标优化问题&#xff08;MOPs&#xff…

短诗《腊八粥》

《腊八粥》现•佚名已买花生同煮粥&#xff0c;粥不似&#xff0c;少年稠也不复&#xff0c;少年仇亦不赴&#xff0c;少年愁终不负&#xff0c;少年筹 &#xff08;主编目前所有分类&#xff1a; 身&#xff0c;心&#xff0c;灵思 工作&#xff0c;生活 创作 剧 让世界更…

封装深拷贝方法

前言 在今年的四月份我写了一篇有关深拷贝的博客文章 我与深拷贝_radash 深拷贝-CSDN博客。在该文章中有一个令我感到遗憾的点就是我没有实现一个自己手写的深拷贝。如今我想弥补当初的遗憾&#xff0c;在这篇文章中详细的讲述一下如何手写一个深拷贝方法。 lodash中是如何实…

数据结构:树

数据结构中的树 树&#xff08;Tree&#xff09;是一种非线性数据结构&#xff0c;用于表示具有层次结构的数据。树结构由节点&#xff08;Node&#xff09;和边&#xff08;Edge&#xff09;组成&#xff0c;节点之间通过边连接&#xff0c;形成父子关系。树是一种抽象数据类…

【信息系统项目管理师】第15章:项目风险管理过程详解

更多内容请见: 备考信息系统项目管理师-专栏介绍和目录 文章目录 一、规划风险管理1、输入2、工具与技术3、输出二、识别风险1、输入2、工具与技术3、输出三、实施定性风险分析1、输入2、工具与技术3、输出四、实施定量风险分析1、输入2、工具与技术3、输出五、规划风险应对1、…

flutter web 路由问题

开发问题背景&#xff1a; flutte 项目中开发网页暴露出来供外部的 网页调用&#xff0c;并不是跳转到项目的首页 项目中使用的路由是 GetX 4.6.0 存在的问题 跳回到首页的问题 web -> flutterflutter 使用 history.back 到web&#xff0c;web forward 到 flutter 此时…

在不到 5 分钟的时间内将威胁情报 PDF 添加为 AI 助手的自定义知识

作者&#xff1a;来自 Elastic jamesspi 安全运营团队通常会维护威胁情报报告的存储库&#xff0c;这些报告包含由报告提供商生成的大量知识。然而&#xff0c;挑战在于&#xff0c;这些报告的内容通常以 PDF 格式存在&#xff0c;使得在处理安全事件或调查时难以检索和引用相关…

二、模型训练与优化遇到的问题1:python=3.10:指定 Python 版本为 3.10。这里为什么指定版本为3.10,有什么依据

目录 一、Python 版本选择的依据 1. TensorFlow 和 Keras 的兼容性 2. Python 3.10 的优势 二、如何选择适合的 Python 版本 1. 检查 TensorFlow 的官方兼容性文档 2. 选择受支持且稳定的版本 3. 避免使用过于旧或过新的版本 三、如何在 Anaconda 中选择不同的 Python …

探索 Vue.js 的动态样式与交互:一个有趣的样式调整应用

修改日期备注2025.1.3初版 一、前言 今天和大家分享在 Vue.js 学习过程中开发的超酷的小应用。这个应用可以让我们通过一些简单的交互元素&#xff0c;如复选框、下拉菜单和输入框&#xff0c;来动态地改变页面上元素的样式哦 让我们一起深入了解一下这个项目的实现过程&…

css出现边框

前言 正常情况下&#xff0c;开启 contenteditable 属性后会出现 “黑色边框”。 如下图所示&#xff0c;很影响美观&#xff1a; 您可能想去掉它&#xff0c;就像下面这样&#xff1a; 解决方案 通过选择器&#xff0c;将 focus 聚焦时移除 outline 属性即可。 如下代码所示&a…

恋爱脑学编程之C++模板编程大冒险

一、模板编程初相识&#xff1a;开启泛型编程魔法之旅 嘿&#xff0c;小伙伴们&#xff01;今天咱们要一起探索C中超级厉害的模板编程。它就像是一把万能钥匙&#xff0c;可以打开各种类型数据的大门&#xff0c;让咱们写出超酷的与类型无关的代码&#xff0c;大大提高代码的复…

ubuntu 20.04 安装 5.4 内核

最近需要用linux 5.4内核&#xff08;发现它和5.14 在Block层有些差异&#xff09;&#xff0c;以对比和5.14内核的差异。目前已安装的虚拟机&#xff0c;Centos8的默认内核是4.18&#xff0c;Redhat9.1的内核是5.14&#xff0c;Ubuntu20.04的内核是5.15&#xff0c;故在ubuntu…

enzymejest TDD与BDD开发实战

一、前端自动化测试需要测什么 1. 函数的执行逻辑&#xff0c;对于给定的输入&#xff0c;输出是否符合预期。 2. 用户行为的响应逻辑。 - 对于单元测试而言&#xff0c;测试粒度较细&#xff0c;需要测试内部状态的变更与相应函数是否成功被调用。 - 对于集成测试而言&a…

netty解码器LengthFieldBasedFrameDecoder用法详解

Netty Netty是一个高性能、异步事件驱动的网络应用程序框架,它提供了对并发和异步编程的抽象,使得开发网络应用程序变得更加简单和高效。 在Netty中,EventLoopGroup是处理I/O操作的多线程事件循环器。在上面的示例中,我们创建了两个EventLoopGroup实例:bossGroup和worker…

继承(5)

大家好&#xff0c;今天我们继续来学习继承的相关知识&#xff0c;来看看子类构造方法&#xff08;也叫做构造器&#xff09;是如何做的。 1.6 子类构造方法 父子父子,先有父再有子,即:子类对象构选时,需要先调用基类构造方法,然后执行子类的构造方法 ★此时虽然执行了父类的…

Spring Boot 依赖配置分离多种打包方式

生产上发布 Spring Boot 项目时,但凡代码有一丁点改动,就得把整个项目包括依赖重新打包上传部署,这样的包很大,影响效率 为解决这个问题,可以把依赖(pom中的依赖jar包)、配置文件(resources 下的 applacation.yml 等文件)从项目主体里剥离出来,后续部署时,只需发布代…

VulnHub-Acid(1/100)

参考链接&#xff1a; ​​​​​​​【VulnHub】Acid靶场复盘-CSDN博客 靶场渗透&#xff08;二&#xff09;——Acid渗透_ambassador 靶场渗透-CSDN博客 网络安全从0到0.5之Acid靶机实战渗透测试 | CN-SEC 中文网 Vulnhub靶场渗透练习(四) Acid - 紅人 - 博客园 红日团队…

51c自动驾驶~合集45

我自己的原文哦~ https://blog.51cto.com/whaosoft/13020031 #运动控制和规划控制需要掌握的技术栈~ 各大垃圾家电造车厂又要开始了~~~​ 1、ROS的通信方式 李是Lyapunov的李&#xff1a;谈谈ROS的通信机制 话题通信和服务通信&#xff0c;其中话题通信是通过发布和订阅…

Debian、Ubuntu 22.04和ubuntu 24.04国内镜像源(包括 docker 源)

Debian 更换国内清华源 1、备份原文件mv /etc/apt/sources.list /etc/apt/sources.list.old 2、写入新源&#xff0c;以下是 Debian 11 的&#xff1a; cat > /etc/apt/sources.list << EOF deb https://mirrors.tuna.tsinghua.edu.cn/debian/ bullseye main contrib…