当前位置: 首页 > article >正文

一个经典嵌入式问题:如何安全读取 64 位计时器

在一个嵌入式系统中需要读取一个持续自增的 64-bit 硬件计时器。由于系统只能通过 32-bit MMIO register 访问该计时器所以硬件把它拆成两个 32-bit 寄存器#define TIMER_LOW_ADDR 0x40001000 #define TIMER_HIGH_ADDR 0x40001010其中TIMER_LOW 表示 timer[31:0] TIMER_HIGH 表示 timer[63:32]计时器会持续递增。当低 32 位从0xFFFFFFFF - 0x00000000发生回绕时高 32 位会加 1。请实现uint64_t read_timer(void);要求安全地返回一个一致的 64-bit timer 值。这个题的考点主要是读取高低位时可能发生的race condition. 考虑以下情况硬件寄存器一开始的值比如HIGH 0x00000001LOW 0xffffffff先读取HIGH: 读到 0x00000001然后在读 LOW 之前timer tick 了一次HIGH 0x00000002LOW 0x00000000再读LOW: 读到 0x00000000如果直接拼0x00000001_00000000这就是错的因为真实时间已经至少是0x00000002_00000000同样的如果我们先读LOW: 读到 0xffffffff然后在读 HIGH 之前timer tick 了一次HIGH 0x00000002LOW 0x00000000再读HIGH: 读到 0x00000002如果直接拼0x00000002_ffffffff这也是错的因为我们的LOW已经wrap 应该读成0x00000002_00000000解决核心是多读一次 HIGH并比较两次 HIGH 的值。如果 hi1 hi2说明在读取 LOW 的前后HIGH 没有变化也就是 LOW 没有发生 wrap-around 进位。因此 LOW 是在同一个 high epoch 下读取到的可以安全拼接(hi1 32) | low如果 hi1 ! hi2说明在两次读取 HIGH 之间LOW 发生了 overflow导致 HIGH 被更新。此时读到的 LOW 可能属于新的 high epoch而第一次 HIGH 属于旧的 epoch所以组合结果不一致需要重新读取直到两次 HIGH 相等。为什么不多读一次 LOW因为 LOW 一直在变。多读 LOW 只能告诉你“时间过了”但不能可靠判断有没有跨过0xffffffff - 0x00000000这个边界。真正有意义的标志是HIGH 有没有变化。 因为 HIGH 只在 LOW wrap 时变化。有了核心思路实现就变得很简单。#define TIMER_LOW_ADDR 0x40001000u #define TIMER_HIGH_ADDR 0x40001010u #define LOW32_REG (*(volatile uint32_t *)TIMER_LOW_ADDR) #define HIGH32_REG (*(volatile uint32_t *)TIMER_HIGH_ADDR) uint64_t read_timer(void) { uint32_t hi1, hi2, lo; do { hi1 HIGH32_REG; lo LOW32_REG; hi2 HIGH32_REG; } while (hi1 ! hi2); return (((uint64_t)hi1 32) | lo); }代码的细节有几点要注意访问MMIO 寄存器有了 MMIO memory address 后需要把地址 cast 成对应宽度的指针(volatile uint32_t *)TIMER_LOW_ADDR这里uint32_t *表示一次读取 32-bitvolatile表示这个地址背后的值可能被硬件随时改变编译器不能缓存、合并或省略读取。然后通过解引用读取寄存器值*(volatile uint32_t *)TIMER_LOW_ADDR所以通常写成宏#define LOW32_REG (*(volatile uint32_t *)TIMER_LOW_ADDR)2. 拼接 64-bit 结果高 32 位要先 cast 成uint64_t再左移 32 bit((uint64_t)hi1 32)然后用 bitwise OR 拼接低 32 位return (((uint64_t)hi1 32) | lo);

相关文章:

一个经典嵌入式问题:如何安全读取 64 位计时器

在一个嵌入式系统中,需要读取一个持续自增的 64-bit 硬件计时器。由于系统只能通过 32-bit MMIO register 访问该计时器,所以硬件把它拆成两个 32-bit 寄存器:#define TIMER_LOW_ADDR 0x40001000 #define TIMER_HIGH_ADDR 0x40001010其中&…...

基于大语言模型的学术论文阅读辅助分析系统的研究与应用

基于大语言模型的学术论文阅读辅助分析系统的研究与应用 摘要 随着科研论文数量的指数级增长,科研工作者面临着前所未有的信息过载挑战。传统学术论文阅读方式依赖线性文本呈现,难以快速定位关键信息,跨文献知识整合效率低下。大语言模型的发展为解决这一问题提供了新的技…...

宏和电子冲刺港股:年营收11.7亿,利润2亿 股价一年上涨超10倍 市值1213亿

雷递网 雷建平 5月17日宏和电子材料科技股份有限公司(简称:“宏和电子”)日前递交招股书,准备在港交所上市。宏和电子2019年7月已在上交所上市。宏和科技在2025年5月时股价才9元,但一年时间股价上涨超过10倍&#xff0…...

理发师会被 AI 取代吗?这可能是 AI 时代最有意思的一个社会学问题

今天去理发了。对着镜子,看着我的头发随着剪刀的飞舞一点点掉下来时,我忽然开始神游:AI 会不会取代理发师? 这问题乍一听有点像胡思乱想,可越想越觉得,它其实非常适合拿来当成 AI 时代的一块切片。 因为理发…...

企业内如何利用Taotoken实现APIKey的集中管理与审计追溯

🚀 告别海外账号与网络限制!稳定直连全球优质大模型,限时半价接入中。 👉 点击领取海量免费额度 企业内如何利用Taotoken实现APIKey的集中管理与审计追溯 对于需要将大模型能力集成到业务流程中的企业而言,管理多个开…...

51单片机驱动SG90舵机:从PWM原理到按键控制实战

1. SG90舵机与51单片机的基础认知 第一次接触SG90舵机时,我盯着那三根彩色导线发愣——这玩意儿怎么就能精准控制角度呢?后来发现它其实是微型伺服系统的典型代表,红色接5V电源,褐色接地线,黄色信号线接任意IO口&#…...

Arm DynamIQ架构缓存一致性协议解析与优化

1. Arm DynamIQ架构中的缓存一致性技术解析在异构计算架构中,缓存一致性协议是确保多核处理器高效协同工作的关键技术。作为Arm体系结构的重要组成部分,DynamIQ共享单元(DSU)通过AMBA ACE和CHI协议实现了灵活的系统级缓存一致性管理。这两种协议虽然设计…...

STM32驱动段码屏实战:手把手教你用HT1621B做个简易电子钟(附完整代码)

STM32与HT1621B打造高精度电子钟:从硬件连接到动态显示全解析 在嵌入式开发领域,能够将理论知识转化为实际项目的能力至关重要。本文将带您完成一个完整的电子钟项目,使用STM32微控制器和HT1621B驱动器来驱动段码液晶屏。不同于简单的驱动演示…...

在模型广场中根据任务需求与预算选择合适的模型

🚀 告别海外账号与网络限制!稳定直连全球优质大模型,限时半价接入中。 👉 点击领取海量免费额度 在模型广场中根据任务需求与预算选择合适的模型 面对文本生成、代码编写、逻辑推理等多样化的任务,开发者常常需要从众…...

JetBrains IDE终极代码高亮指南:MultiHighlight让复杂代码一目了然

JetBrains IDE终极代码高亮指南:MultiHighlight让复杂代码一目了然 【免费下载链接】MultiHighlight Jetbrains IDE plugin: highlight identifiers with custom colors 🎨💡 项目地址: https://gitcode.com/gh_mirrors/mu/MultiHighlight …...

离线语音模块在塔扇智能化中的集成与应用实践

1. 项目概述:当塔扇“听懂”你的话 家里的塔式风扇,你是不是也经常遇到这样的场景:晚上躺在床上,风扇对着吹有点冷,想调小一档或者关掉,结果发现遥控器不知道被塞到哪个沙发缝里了,只能挣扎着爬…...

3分钟搞定网易云音乐NCM解密:ncmdump工具让你的音乐随处播放

3分钟搞定网易云音乐NCM解密:ncmdump工具让你的音乐随处播放 【免费下载链接】ncmdump 项目地址: https://gitcode.com/gh_mirrors/ncmd/ncmdump 你是否曾为网易云音乐下载的歌曲只能在特定客户端播放而烦恼?当你想要在车载音响、智能音箱或其他…...

应用连接协议桥接器:打通异构系统,实现数据自动化流转

1. 项目概述:一个连接不同应用生态的“桥梁”最近在折腾一些自动化流程,发现不同平台、不同应用之间的数据互通是个老大难问题。比如,你在A平台创建了一个任务,希望它能自动同步到B平台的日历,或者把C应用里的数据变化…...

告别模组冲突:3分钟掌握Nexus Mods App终极游戏模组管理方案

告别模组冲突:3分钟掌握Nexus Mods App终极游戏模组管理方案 【免费下载链接】NexusMods.App Home of the development of the Nexus Mods App 项目地址: https://gitcode.com/gh_mirrors/ne/NexusMods.App 还在为《赛博朋克2077》的模组冲突而烦恼吗&#x…...

200块搞定AI视觉项目:手把手教你用Canmv K210训练识别模型(附完整代码)

200元打造AI视觉神器:Canmv K210从模型训练到落地实战指南 在AI技术快速普及的今天,动辄数千元的开发套件让许多创客和学生望而却步。Canmv K210开发板的出现彻底改变了这一局面——仅需200元预算,就能搭建完整的AI视觉识别系统。本文将带你从…...

英雄联盟国服换肤终极指南:R3nzSkin免费体验全皮肤

英雄联盟国服换肤终极指南:R3nzSkin免费体验全皮肤 【免费下载链接】R3nzSkin-For-China-Server Skin changer for League of Legends (LOL) 项目地址: https://gitcode.com/gh_mirrors/r3/R3nzSkin-For-China-Server 厌倦了英雄联盟国服中单调的默认皮肤&am…...

手把手教你用Vivado 2019.1和Tri Mode Ethernet MAC IP,在Artix-7上搞定千兆UDP通信(附RTL8211E/YT8531C/KSZ9031配置)

基于Artix-7的千兆以太网UDP通信实战指南 在嵌入式系统开发中,实现稳定可靠的网络通信一直是工程师面临的挑战之一。特别是当项目需要高速数据传输时,如何选择合适的硬件平台和协议栈就显得尤为重要。本文将聚焦Xilinx Artix-7 FPGA平台,详细…...

AI智能体集群如何革新代码审查:架构、实现与CI/CD集成

1. 项目概述:一个为代码审查提效的智能体集群如果你是一名团队的技术负责人或资深开发者,肯定对代码审查(Code Review)这个环节又爱又恨。爱的是,它是保证代码质量、促进知识共享的关键闸门;恨的是&#xf…...

代码编辑器世纪大战:VS Code vs JetBrains IDE vs Zed全面对比

Visual Studio Code、IntelliJ IDEA/PhpStorm/WebStorm、Zed——这三种编辑器代表了三代程序员的生产力哲学。本文从响应速度、生态成熟度、AI赋能、协作能力四个维度进行深度横评。 一、三种编辑器的基因差异 VS Code:开放生态的胜利 VS Code的核心优势不是功能&am…...

米尔i.MX 93核心板:异构计算与AI赋能入门级嵌入式开发实战

1. 项目概述:米尔NXP i.MX 93核心板如何重塑入门级嵌入式体验 在嵌入式开发领域,选型往往是一场在性能、成本和功能之间的艰难平衡。对于许多从事工业HMI、智能网关、便携式医疗设备或新能源充电桩开发的工程师来说,他们既需要一颗能流畅运行…...

【信息科学与工程学】计算机科学与自动化——第二百篇 综合类算法篇01

Net-B1-001 Transformer 推理引擎 列 内容 (对应“大规模预训练Transformer模型的推理与优化”) 编号​ Net-B1-001 类型​ AI推理与优化系统 领域​ 人工智能 / 深度学习 模块​ Transformer 推理引擎 内存模式【主内存/GPU内的内存/Soc中的内存/其他芯片中的内存】…...

点式玻璃幕墙及采光顶设计的一些想法

点式玻璃幕墙及采光顶设计的一些想法 点式玻璃幕墙是在主龙骨上面固定点支撑装置,由点支撑装置支撑玻璃面板的一种常用幕墙表现形式,他最早起源于国外。因为玻璃的通透性,建筑内外有效融合,空间感增强,开阔了视野,增加了建筑物的现代感。 点式玻璃幕墙最主要的组成部分是…...

FastGithub终极加速指南:3步解决GitHub访问卡顿难题

FastGithub终极加速指南:3步解决GitHub访问卡顿难题 【免费下载链接】FastGithub github定制版的dns服务,解析访问github最快的ip 项目地址: https://gitcode.com/gh_mirrors/fa/FastGithub GitHub加速是每个国内开发者都关心的话题。你是否经常因…...

Linux服务器文件传输服务搭建:从FTP协议到vsftpd实战部署

1. 项目概述:为什么要在Linux上搭建FTP服务器?很多刚接触Linux的朋友,尤其是从Windows转过来的,一提到搭建服务器,特别是像FTP这种“古老”但依然实用的文件传输服务,第一反应可能就是“头大”。在Windows上…...

TencentDB Agent Memory 架构拆解:告别 Agent 失忆,构建四层可追溯记忆与上下文治理系统

拆解 TencentDB Agent Memory 如何用分层记忆、上下文卸载和降级检索,让 Agent 留住工作现场。 原文链接:AI 小老六 Agent 真正难用的地方,往往不是它不会调用工具,而是它记不住工作现场。 你刚给它讲完项目背景、编码偏好、部署…...

如何在10分钟内搭建自己的游戏串流服务器:Sunshine开源游戏串流完整教程

如何在10分钟内搭建自己的游戏串流服务器:Sunshine开源游戏串流完整教程 【免费下载链接】Sunshine Self-hosted game stream host for Moonlight. 项目地址: https://gitcode.com/GitHub_Trending/su/Sunshine 想在任何设备上玩PC游戏吗?Sunshin…...

RK3588开发板Debian系统从零配置到实战:安全加固、Docker部署与性能调优

1. 项目概述:从零上手TL3588的Debian系统最近在折腾一块基于瑞芯微RK3588芯片的开发板,型号是TL3588。这板子性能是真不错,八核CPU加上强大的NPU,拿来做边缘计算、多媒体网关或者轻量级服务器都挺合适。但刚拿到手,面对…...

终极窗口分辨率自定义指南:SRWE如何突破显示限制

终极窗口分辨率自定义指南:SRWE如何突破显示限制 【免费下载链接】SRWE Simple Runtime Window Editor 项目地址: https://gitcode.com/gh_mirrors/sr/SRWE 在数字创作和游戏体验的领域中,窗口分辨率自定义工具SRWE(Simple Runtime Wi…...

在Windows上直接安装APK的完整指南:告别模拟器时代

在Windows上直接安装APK的完整指南:告别模拟器时代 【免费下载链接】APK-Installer An Android Application Installer for Windows 项目地址: https://gitcode.com/GitHub_Trending/ap/APK-Installer 你是否曾想过,在Windows电脑上直接运行Andro…...

自托管MCP服务器模板:快速构建AI智能体私有工具箱

1. 项目概述:一个为AI智能体赋能的“工具箱”模板最近在折腾AI智能体(Agent)开发的朋友,可能都听说过MCP(Model Context Protocol)这个概念。简单来说,MCP就像是为AI大模型准备的一套标准化的“…...