将python中的IEEE浮点数转换为TI TMS320C30 32位浮点数 [英] Convert IEEE float to TI TMS320C30 32bits float in python

查看:94
本文介绍了将python中的IEEE浮点数转换为TI TMS320C30 32位浮点数的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我需要按照以下约定将python float转换为TI DSP TMS320C30 float表示形式:

I need to convert a python float to a TI DSP TMS320C30 float representation, following this convention:

http://www.ti.com/lit/an/spra400/spra400.pdf#page=13

我已经尝试了一些方法,但是似乎无法将所提出的算法笼罩在脑海中.我还发现了

I've tried a few things, but I can't seem to wrap my head around the proposed algorithm. I also found a C version of the algorithm, but it looks like it is a version that runs in the TI DSP, so there are operations that I can't figure out (reverse the sign, for instance).

我在下面有一个非常幼稚的实现,但是它不起作用...

I have a very naive implementation below, but it doesn't work...

# see http://www.ti.com/lit/an/spra400/spra400.pdf

import math

def twos_comp(val, bits):
    """compute the 2's complement of int value val"""
    if( (val&(1<<(bits-1))) != 0 ):
        val = val - (1<<bits)
    return val

def float_to_ti( f ):
    m,e = math.frexp( f )
    # print m, e,
    mantissa = int(str(m)[2:])
    exponent = twos_comp((e - 127), 8) if e != 0 else (-128)
    sign = 1 if f < 0 else 0
    # print sign, mantissa, exponent
    return ((sign << 30) + (exponent << 24) + mantissa) & 0xffffffff

一些期望值的例子:

# Float     TI Decimal value of the resulting 32bits
#################################################
# 0.0         2147483648
# 1.0         0
# 100         105381888
# 0.000021    4029688104
# 10          52428800
# -1.0        4286578688
# -10.0       65011712
# -0.0021     4160118745
# -84.5487    114747153

我认为它可以归结为python返回尾数/有效位数的方式,但我不确定.
您如何从这里开始?

I think it boils down to the way python returns the mantissa/significand, but I'm not sure.
How would you start things here?

注意:我发现了此问题可能相关,我将研究一下struct pack并解压缩.

Note: I found this question that might be related, I'll look into the struct pack and unpack..

FYI:我用C程序检索了理论值,该程序是这样加载到DSP中的:

FYI: I retrieved the theoretical values with a C program that I load in the DSP like this:

{
  float f = -1.0; printf("F: %f -> %u", f, *(unsigned int*)&f);
  f = -10.0;      printf("F: %f -> %u", f, *(unsigned int*)&f);
  f = -0.0021;    printf("F: %f -> %u", f, *(unsigned int*)&f);
  f = -84.5487;   printf("F: %f -> %u", f, *(unsigned int*)&f);
}

有效的实施方式

按照阿明的回答,我知道它适用于负数:

Working implementation

Following Armin's answer, I got it working for negative numbers:

def float_to_ti(f):
    m, e = math.frexp(f)
    ma = m
    m = abs(m * 2)
    e -= 1
    sign = (math.copysign(1.0, f) < 0)
    man = int((m - 1.0) * (1 << 23))
    if sign:
        man *= -1
    if e == 0 and sign == 1:
        e = 255
    if f == 0.0:
        return (128 << 24) | (sign << 23)
    return ((e & 0xff) << 24) | (sign << 23) | man & 0x7fffff

推荐答案

以下代码通过了您的测试:

The following code passes your tests:

def float_to_ti( f ):
    m, e = math.frexp(f)
    m *= 2
    e -= 1
    sign = (math.copysign(1.0, f) < 0)
    if f == 0.0:
        return (128 << 24) | (sign << 23)
    if sign:
        m += 2.0
        if m == 1.0:
            m = 0.0
            e -= 1
    else:
        m -= 1.0
    assert 0.0 <= m < 1.0
    return ((e & 0xff) << 24) | (sign << 23) | int(m * (1 << 23) + 0.5)

请注意不同的顺序(指数,符号,尾数).还要注意math.frexp()不会以IEEE格式返回任何内容,因此该代码不必担心任何IEEE细节:(e& 0xff)转换指数(作为签名字符)转换为未签名的数字.最后,请注意,C30格式不支持反规范,这意味着隐含了尾数的最高位(因此 m-1.0 ).

Note the different order (exponent, sign, mantissa). Note also that math.frexp() doesn't return anything in the IEEE format, so this code doesn't worry about any IEEE details: the (e & 0xff) converts the exponent (as a signed char) to an unsigned number. Finally, note that the C30 format doesn't support denormals, which means that its mantissa's top bit is implied (hence the m - 1.0).

这篇关于将python中的IEEE浮点数转换为TI TMS320C30 32位浮点数的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆