Vdsp(bf561)中的浮点运算(12):fract16加减运算

快乐虾

http://blog.csdn.net/lights_joy/

lights@hb165.com

 

本文适用于

ADSP-BF561

Visual DSP++ 5.0 (update 6)

Vdsp dual processor simulate

 

欢迎转载,但请保留作者信息

 

由于减法实际可以看成加上一个负数,因此我们只需要看加法操作。fract16的加法运算由add_fr1x16函数完成:

#pragma inline

#pragma always_inline

static fract16  add_fr1x16(fract16  __a, fract16  __b) {

  fract16  __rval = __builtin_add_fr1x16(__a, __b);

  return __rval;

}

从这里可以看出我们实际可以使用__builtin_add_fr1x16这一函数调用。

写一个很简单的程序:

typedef fract16 ft;

 

ft calc(ft x, ft y)

{

       ft r;

       r = __builtin_add_fr1x16(x, y);

       return r;

}

这个函数展开后的汇编代码为:

_calc:

.LN_calc:

//-------------------------------------------------------------------

//   Procedure statistics:

//   Frame size            = 8

//   Scratch registers used:{R0.L,R0.H,R1.L,ASTAT0-ASTAT1}

//   Call preserved registers used:{FP,SP,RETS}

//-------------------------------------------------------------------

// line "./float_test.c":27

       LINK 0;

       W[FP + 12] = R1;

       W[FP + 8] = R0;

.LN0:

// line 29

       R0.L = R1.L + R0.L (S);

       R0 = R0.L (X);

       W[FP + 16] = R0;

.LN1:

// line 30

       UNLINK;

       RTS;

.LN._calc.end:

._calc.end:

       .global _calc;

       .type _calc,STT_FUNC;

可以发现,__builtin_add_fr1x16展开后的汇编代码就是

       R0.L = R1.L + R0.L (S);

因而完成这样一个加法运算将只需要一个cycle的时间。

VDSP的文档里这样介绍这条指令:

Data Registers — 16-Bit Operands, 16-Bit Result

Dreg_lo_hi = Dreg_lo_hi + Dreg_lo_hi (sat_flag) ;    /* (b) */

Dreg_lo_hi: R7–0.L, R7–0.H

sat_flag: nonoptional saturation flag, (S) or (NS)

In the syntax, where sat_flag appears, substitute one of the following values.

(S) – saturate the result

(NS) – no saturation

由于这是一条带符号的加法指令,因此它将有一个饱和问题:

Saturation is a technique used to contain the quantity within the values that the destination register can represent. When a value is computed that exceeds the capacity of the destination register, then the value written to the register is the largest value that the register can hold with the same sign as the original.

If an operation would otherwise cause a positive value to overflow and become negative, instead, saturation limits the result to the maximum positive value for the size register being used.

Conversely, if an operation would otherwise cause a negative value to overflow and become positive, saturation limits the result to the maximum negative value for the register size.

The maximum positive value in a 16-bit register is 0x7FFF. The maximum negative value is 0x8000. For a signed two’s-complement 1.15 fractional notation, the allowable range is –1 through (1–2–15).

当两个数相加超过fract16所能表示的最大值时,它将直接返回fract16所能表示的最大值0x7fff,即0.999969482421875,当结果小于-1时,它将返回-1

由于fract16不是内置类型,而是定义为short,我们看看如果不使用__builtin_add_fr1x16而是直接用加号会发生什么:

typedef fract16 ft;

 

ft calc(ft x, ft y)

{

       ft r;

       r = x + y;

       return r;

}

汇编输出变成了:

// line 29

       R0 = R0 + R1 (NS);

       R0 = R0.L (X);

       W[FP + 16] = R0;

区别还是很大的,编译器把它变成了32位加法再取低16位,这样就不会是返回饱和的结果了,而是返回一个不希望看到的数字,呵呵。

减法与此类似,不过改为调用下面的函数调用而已:

#pragma inline

#pragma always_inline

static fract16  sub_fr1x16(fract16  __a, fract16  __b) {

  fract16  __rval = __builtin_sub_fr1x16(__a, __b);

  return __rval;

}

 

 

 

 

1       参考资料

Vdsp(bf561)中的浮点运算(11):fract16float的转换(2009-8-17)

Vdsp(bf561)中的浮点运算(10):fract16类型表示(2009-8-17)

Vdsp(bf561)中的浮点运算(9):long doublefloat的比较(2009-8-14)

Vdsp(bf561)中的浮点运算(8):float除法运算(2009-8-14)

Vdsp(bf561)中的浮点运算(7):float乘法运算(2009-8-13)

Vdsp(bf561)中的浮点运算(6):float加减运算(2009-8-13)

Vdsp(bf561)中的浮点运算(5):float类型表示总结(2009-8-12)

Vdsp(bf561)中的浮点运算(4):FLT_MAX(2009-8-12)

Vdsp(bf561)中的浮点运算(3):FLT_MIN(2008-12-19)

Vdsp(bf561)中的浮点运算(2):float的疑问(2008-12-18)

Vdsp(bf561)中的浮点运算(1):文档的说法(2008-12-16)

 

 

 

 

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

嵌云阁主

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值