首页 文章

类型转换VHDL

提问于
浏览
1

我正在尝试为MS5541C压力/温度传感器编写驱动程序,但看起来我似乎无法做到 . 数据表提供了一些计算,如果我把它们放入excel似乎工作得很好 . 但是,当我尝试为它编写VHDL代码并将其显示在7段显示器上时,它不起作用 .

提供的计算是:

UT1 = 8 * C5 + 10000

其中C5是从PROM读取的校准数据

dT = D2 - UT1

其中D2是从DAC读取的温度

TEMP = 200 + dT*(C6+100)/2^11

其中temp是0.1摄氏度的实际温度,C6也是校准温度 .

在我的情况下,C5 = 2223(dec),D2 = 28144(dec),C6 = 53.使用这些数字,我得到22.7摄氏度的温度 .

我在VHDL中使用的代码(MCVE)是:

LIBRARY IEEE;
USE IEEE.STD_LOGIC_1164.ALL;

use ieee.numeric_std.all;

ENTITY MS5541C_CONVERTER IS

PORT(
        CLK     : IN STD_LOGIC;
    RST     : IN STD_LOGIC;

    T_OUT   : OUT STD_LOGIC_VECTOR(15 DOWNTO 0)
);
END ENTITY;

ARCHITECTURE MS5541C_CONVERTER OF MS5541C_CONVERTER IS

Constant C5     : STD_LOGIC_VECTOR(11 DOWNTO 0) := "100010101111"; -- Reference temperature
Constant C6     : STD_LOGIC_VECTOR( 6 DOWNTO 0) := "0110101"; -- Temp coefficient of the temperature

Constant D2     : STD_LOGIC_VECTOR(15 DOWNTO 0) := x"6df0"; -- temperature

BEGIN

PROCESS (CLK,RST) 
    VARIABLE UT1    : SIGNED(33 DOWNTO 0);
    VARIABLE dT     : SIGNED(33 DOWNTO 0);
    VARIABLE TEMPE  : SIGNED(33 DOWNTO 0);
    VARIABLE C5_s   : SIGNED(33 DOWNTO 0);
    VARIABLE C6_s   : SIGNED(33 DOWNTO 0);
BEGIN
    C5_s := RESIZE(signed(C5),33);
    C6_s := RESIZE(signed(C6),33);
    IF RST = '1' THEN

    ELSIF rising_edge(CLK) THEN
        UT1 := 8 * C5_s + 10000;
        dT  := RESIZE(signed(D2),33) - UT1;
        TEMPE := 200 + dT*(C6_s + 100)/ 2048;
        T_OUT <= STD_LOGIC_VECTOR(RESIZE(TEMPE,16));
    END If;
END PROCESS;
END ARCHITECTURE;

结果是2674(dec)或a72(hex)(实际数字可能与excel略有不同,因为这是两次测量,但这甚至不是很接近)

我已经重读了几次计算,甚至尝试了不同的方法,但结果永远不正确 . 我认为它与类型的转换有关,但我不知道是什么 .

附:对于想要阅读数据表的人:

http://media.digikey.com/pdf/Data%20Sheets/Measurement%20Specialties%20PDFs/MS5541-CM.pdf

1 回答

  • 0

    至少有一个问题是,当您对C5进行签名转换时,将保留-4984而不是2223.然后将此负数扩展为33位宽 .

    如果这是唯一的问题,你的最终结果将是4534,所以可能存在另一个问题,但是你转换为signed的其他常量都没有一个领先 '1' .

    C5,C6,D2实际上是否有数字?它们实际上是从舞会上读取的12/7/16位宽吗?

    我希望你的时钟非常慢,或者这不是为了合成,尽管我怀疑你打算在真正的系统中使用它 . 这种使用变量而不是信号的数学运算将在一个时钟周期内完成所有这些工作 . 33位操作数(广泛的一面)加剧了这个问题 .

    说到操作数长度,如果计算出每个计算和操作数将保持的最大值并使用适当的长度,则数学效率会更高 . 优化器可以修复其中一些,但它们并不总是完美的 .

相关问题