十年匠心定制 · 商业建站与技术教学双线并行 咨询热线:400-886-1026 service@lmnt.cn
ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

CS5532/CS5513程序移植:从CS55XX.rar提取代码与软SPI实现

CS5532/CS5513程序移植:从CS55XX.rar提取代码与软SPI实现 简介CS5513和CS5532是常用于嵌入式系统与工业控制的芯片开发者通常需要为其编写底层驱动与引导代码才能完成初始化、数据传输和外部设备通信。压缩包内共4个文件包括2个C源文件和2个头文件整体体积仅5KB结构非常精简阅读门槛低适合直接查看、修改和移植。C源文件主要承载初始化配置、数据传输等核心逻辑头文件则用于声明接口和寄存器宏定义便于在集成开发环境中快速调用和二次开发。内容还涉及CS5513的引导加载与启动初始化部分以及CS5532的寄存器配置和通信接口封装对UART、SPI、I2C等常见总线的驱动适配有直接的代码级参考价值。目前已有560人学习下载既适合嵌入式初学者借此理解芯片驱动结构也适合有经验的工程师在现有项目中快速集成或定位通信故障。1. CS55XX.rar 里的 CS5513/CS5532 程序先别急着烧录搜到 CS55XX.rar 的人大多是刚接手一块带称重、拉力或者桥式传感器的板子手里只有一个从同事或旧电脑里转存下来的压缩包。文件名写着CS55XX里面同时出现 CS5513 和 CS5532看起来是同一套程序实际差异很大CS5513 是低成本单通道方案CS5532 是双通道高分辨率方案两者的 SPI 命令字、寄存器布局和通道处理逻辑都不完全互通。最怕的就是直接把某个main.c里的初始化函数抄进新工程编译过了但读回来的数永远是满码或零。这篇不介绍某个下载站里的软件而是把 CS55XX.rar 当作一个现成代码库来翻先筛出里面能用的程序文件再讲软 SPI 读写、一轮采样流程、通道与校准参数怎么设最后用三个电工级检查点验证移植是否成功。适合想用最短时间让 CS5532 在 51、STM32 或国产单片机平台上出数的人也适合需要把旧例程改成自己板子引脚的人。2. 从 CS55XX.rar 里筛 CS5513/CS5532 程序先看清单再看引脚2.1 解压前先列出包内结构按芯片名过滤文件拿到压缩包不要直接右键全部解压到桌面先看里面有没有针对 CS5513 和 CS5532 的独立工程。Windows 下装了 WinRAR 可以直接打开查看命令行环境下用unrar l或7z l列目录更干净方便过滤.c、.h和 PDF 文件。unrar l CS55XX.rar | grep -Ei 5532|5531|5533|cs55|\.c$|\.h$|pdf把命令拆开解释unrar l只列出文件内容不做实际解压grep过滤出和芯片型号、源码、原理图、手册相关的条目。Windows 下没有unrar时用7z l CS55XX.rar也能拿到同样的清单只是输出格式略不同。这样做的目的是先判断这个包是“完整参考设计”还是“只有一段抓下来的代码”决定后面是直接编译还是补全底层。常见压缩包其实就三类文件芯片官方参考代码、网友用 51 单片机写的 demo、以及原版数据手册。最值钱的不是某个完整工程而是头文件里的寄存器宏定义和命令字这部分一般能原样搬走。2.2 三类文件能否直接复用的判断表文件类别典型位置复用方式头文件如cs55xx.h、CS5532_Reg.hinclude 或 src 目录尽量整个提取寄存器宏和命令字直接引用初始化加 SPI 的.c文件demo/51 或 demo/stm32函数逻辑可参考引脚和延时必须重写数据手册与应用笔记 PDFdocs 或 doc 目录不是程序但命令字、寄存器位以手册为准为什么不能以为目录名一样就可以整包拿来编译因为多数 CS55XX 例程是给老 Keil C51 写的开头一句#include reg52.h到了 STM32 上直接报错而且里面大量用sbit定义引脚换成标准 GPIO 操作时整个 IO 层都要重写。所以正确思路是只摘函数不搬 main。2.3 把例程里真正值得保留的函数挑出来我一般会在解压后的目录里搜索几个固定函数名如CS55xx_Init、CS55xx_ReadADC、Read_CS5532、delay_us。只要在.c文件里看到这些名字就说明这个程序的核心逻辑已经齐了剩下的按键、显示、串口打印都可以不要。值得保留的部分按顺序排CS55xx_Init()或CS5532_Init()负责 CS、SCLK 引脚初始化上电延时系统复位命令。Delay_us()很多旧例程用while(--i)空转需要改成定时器延时或__NOP()循环。SPI 收发的底层函数不管叫SPI_WriteReadByte还是ReadChar只要是逐字节交换的就是移植主角。命令字宏定义在头文件里搜CMD_或CONV整段复制到新工程。2.4 对照原理图改引脚定义别信原压缩包里的引脚旧工程里最常见的是三个引脚CS、SCLK、SDI/MOSI、SDO/MISO。CS5513 和 CS5532 都是 SPI 从机但参考板的 PCB 可能把 CS 接到了 P3.5你的板子可能接到 PD12。直接在头文件里改宏是最快的做法。#define CS55_SSN_PORT GPIOB #define CS55_SSN_PIN GPIO_PIN_12 #define CS55_SCLK_PORT GPIOB #define CS55_SCLK_PIN GPIO_PIN_13 #define CS55_MOSI_PORT GPIOB #define CS55_MOSI_PIN GPIO_PIN_15 #define CS55_MISO_PORT GPIOB #define CS55_MISO_PIN GPIO_PIN_14这里把 CS、SCLK、MOSI、MISO 都单列成“端口引脚”宏而不是直接写在 GPIO 初始化函数里后面换板子时只需要改这组宏。注意 MOSI 和 MISO 的方向是相对主控来说的CS5513 的 SDI 接主控 MOSISDO 接主控 MISO别在这两个脚上接反接反的结果是命令发得出去但读回全是 0xFF。3. 移植 CS5513/CS5532 程序软 SPI 读写与一轮采样的最小代码3.1 为什么参考程序大多用软 SPI 而不是硬件 SPICS55XX 系列需要的 SPI 时序不复杂但很多国产单片机或 51 移植过来的参考程序都选择软件模拟理由是硬件 SPI 的空闲电平和采样相位不一定符合 CS5532 的默认配置。CS5532 的采样率通常不高根本不需要几 Mbps 的硬件 SPI 速度用普通 GPIO 翻转足够稳定。另一个原因是硬件 SPI 一旦接错引脚排查起来比软件模拟麻烦。软 SPI 至少可以随时用示波器看 SCLK 和 CS 的电平关系错了就在代码里调整不用查复用寄存器。3.2 一个最小但能收到数据的 SPI 读写函数下面的函数把主控侧的单字节发送和接收合并在一起高位先出每个 bit 里先准备 MOSI 电平再拉高 SCLK再在 SCLK 高电平期间采样 MISO。这是 CS55XX 例程里最常见的一组时序。static void cs55_delay_half_clock(void) { for (volatile int i 0; i 8; i) ; // 按主频调整约几十 ns } uint8_t cs55_spi_rw(uint8_t tx) { uint8_t rx 0; for (int i 7; i 0; i--) { if (tx (1 i)) CS55_MOSI_HIGH(); else CS55_MOSI_LOW(); cs55_delay_half_clock(); CS55_SCLK_HIGH(); cs55_delay_half_clock(); if (CS55_MISO_READ()) rx | (1 i); CS55_SCLK_LOW(); } return rx; }代码里几个参数要说明cs55_delay_half_clock的空循环次数决定 SCLK 频率主频越高循环次数越大。循环过短时 SCLK 太快CS5532 可能丢位循环过长只是读得慢不会损坏芯片。MISO 的采样放在 SCLK 高电平期间这是绝大多数 CS55XX 例程的约定实际以你手里 .rar 里带的手册时序图为准。3.3 一轮 CS5532 采样最少要做四件事CS5532 不像普通并口 ADC 那样 CS 一拉低就有数据必须先发命令再读结果。一次单通道采集至少包括启动转换、等待转换完成、拉低 CS、读出数据。void cs5532_single_sample(uint8_t ch, int32_t *value) { uint8_t tmp[4] {0}; // 1. 发启动转换命令宏定义在 cs55xx.h 里 cs55_ssn_low(); cs55_spi_rw(ch 0 ? CS5532_CMD_CONV_CH0 : CS5532_CMD_CONV_CH1); cs55_ssn_high(); // 2. 等待转换完成最省事的是读 busy 引脚或延时一个转换周期 delay_us(200); // 3. 拉低 CS准备读数据 cs55_ssn_low(); for (int i 0; i 4; i) tmp[i] cs55_spi_rw(0xFF); cs55_ssn_high(); // 4. 合并成 24 位有符号数 int32_t raw (int32_t)((tmp[0] 16) | (tmp[1] 8) | tmp[2]); if (raw 0x800000) raw | 0xFF000000; *value raw; }这段代码里四个步骤缺一不可。很多人只记得读数据忘记发启动转换命令结果读到的永远是上一次转换结果。delay_us(200)是保守等待实际延时取决于 CS5532 的输出字率设置写了配置寄存器之后要按公式重算。读出 4 字节里前 3 字节是 24 位数据第 4 字节通常是状态信息这里先不参与计算。3.4 24 位 ADC 转 int32_t 的符号问题CS5532 的输出是二进制补码满量程范围是0x7FFFFF到-0x800000。如果直接把 24 位数据左移 8 位再转int32_t会因为最高位是符号位而导致负数变成很大的正数。处理方式结果(tmp[0] 16)(tmp[1] 8)再判断raw 0x800000并扩展高字节负值正确可以参与浮点换算上面的代码已经做了符号扩展注释里一定要保留这句话否则下次优化代码时很容易误删掉if那一行。4. 把 CS5513 配置改成 CS5532通道、输出字率与校准顺序4.1 需要重点调整的三个配置项CS5513 没有通道切换这种说法读回来的数据直接对应唯一输入。CS5532 则有两条通道代码里要明确写清楚当前采样的是哪个输入否则两个传感器接到同一片 CS5532 时读出来的永远是同一路数据。配置项对程序的影响调试期建议输入通道选择决定启动转换命令里的通道号先用固定通道 0别用动态变量输出字率决定转换完成需要等待的时间先用低速率稳定后再提速单次/连续转换模式决定主循环是轮询还是自动读单次转换最容易定位时序问题配置寄存器的具体位定义在 CS5532 手册里有一张很长的 Bit 表不同 .rar 包里的头文件可能已经把字段拆成宏。我一般不去背每一位而是把头文件里的CS5532_CFG_*宏按手册说明组合成 16 位配置字。4.2 写配置寄存器前先发一次系统复位CS5532 上电后内部寄存器状态不确定直接写配置可能无效。常见的正确顺序是上电延时 — CS 拉高 — 拉低 CS — 发复位命令 — 等待 — 发配置命令。void cs5532_reset_and_wait(void) { cs55_ssn_high(); delay_ms(10); cs55_ssn_low(); cs55_spi_rw(CS5532_CMD_RESET); // 复位命令字来自头文件 delay_ms(20); cs55_ssn_high(); delay_ms(10); }为什么要单独拆一个复位函数因为我在调试时发现有些国产单片机上电速度不稳定CS5532 的复位命令如果跟着配置命令连续发送芯片偶尔会忽略前两条命令。分开写的好处是哪儿出问题可以直接看波形CS 拉低后 SCLK 上有没有完整 8 个脉冲。4.3 通道切换时留出稳定时间CS5532 的通道切换不是简单地改一个 GPIO而是要把通道选择命令通过 SPI 写进芯片内部。切换后不建议立刻启动转换内部模拟开关需要一点建立时间。void cs5532_select_channel(uint8_t ch) { cs55_ssn_low(); cs55_spi_rw(ch 0 ? CS5532_CMD_CH0 : CS5532_CMD_CH1); cs55_ssn_high(); delay_us(10); // 建立时间按手册和实测调整 }这个延时不能只写 1 个微秒。调试时如果把通道命令和启动转换命令连在一起发数据可能会从上一个通道串扰过来。稳妥做法是在两次命令之间留至少 10 微秒实际值可以更大反正 CS5532 的转换周期本身就有几百微秒。4.4 第一次读数的校准顺序CS5532 内部有数字校准寄存器程序上电后要做一次校准否则零点偏移可能造成读数不是零。注意校准命令要分单次校准和连续校准调试期我一般用单次校准void cs5532_self_calibrate(void) { cs55_ssn_low(); cs55_spi_rw(CS5532_CMD_CAL_SELF); // 自校准命令 cs55_ssn_high(); while (cs55_busy_read()); // 等待校准完成 delay_ms(5); }这里cs55_busy_read()对应芯片的忙状态引脚如果板子上没有引出这个引脚就改成固定延时。延时多少要看命令和配置的输出字率保守一点给 100 毫秒也不会影响使用只是每次上电多等一会儿。提示校准命令必须在配置寄存器和通道都设定完成之后执行顺序反了可能校准到旧参数上读回来数值仍然带着偏移。5. 编译 CS5513/CS5532 程序后先测三个点VREF、MISO、校准返回值5.1 先量 VREF 再量 DVCC程序烧进去没反应时先不要怀疑代码逻辑把万用表打在电压档量一下 CS5532 的 DVCC 和 VREF。常见现象是 VREF 悬空ADC 读回来全是满码或跳变。VREF 的电压会直接进入 ADC 的满量程计算公式不是随便接个 5V 就行。用多位数万用表量一次实际值和程序里的vref变量保持一致。5.2 MISO 读出固定值时的首查项如果 SPI 读回来的每个字节都是 0xFF或者都是 0x00优先查四件事CS 有没有在命令期间一直拉低、SCLK 的空闲电平对不对、MISO 上有没有外接上拉电阻、和主控 MISO 引脚有没有复用到其他外设。CS5532 的 MISO 在 CS 为高时会变成高阻如果总线上没有上拉读回 0xFF 很正常。5.3 用已知输入验证校准返回值校准之后不要直接上传感器先接一个已知电压到通道输入用下面这个换算式看线性度float cs5532_to_voltage(int32_t raw, float vref, float gain) { return (float)raw / 8388608.0f * vref / gain; }8388608.0f是 2 的 23 次方对应 24 位 ADC 的满量程中点数。把 0V 和 1.2V 两个已知点分别接到同一通道程序打印出来的换算电压应该接近两个值。再切到另一个通道测试比较两个通道之间的偏差这比单纯看绝对值更能确认通道选择命令有没有写对。最后把 CS55XX.rar 里不同例程的寄存器宏逐行对照一次确认没有新旧头文件混用。本文还有配套的精品资源点击获取
返回列表