找回密码
 注册
关于网站域名变更的通知
查看: 447|回复: 3
打印 上一主题 下一主题

DSP学习经验

[复制链接]

该用户从未签到

跳转到指定楼层
1#
发表于 2016-5-10 17:11 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式

EDA365欢迎您登录!

您需要 登录 才可以下载或查看,没有帐号?注册

x
大学毕业至今,做了三年的DSP开发,将稍许经验记录下来,分享一下。
4 ?' H3 K7 T1 W+ n  一、弄清DSP相关资源的来源及熟读手册+ Q! L( ?9 n" L* a" ^- N! w$ f
  一般主要来源于DSP芯片厂商的官方网站,虽然现在的DSP芯片厂商都提供了中文的官方网站浏览,但我建议还是上英文的网站,其一,有些资源在中文网站上没有(关于这点,我个人认为可能是中文这边的资源未及时上传),其二,一般资料很少有中文版,中文和英文版网站上下载的其实是同一个版本;再就是,要熟悉DSP芯片厂商的官方网站,开发时允分利用官方提供的资源及支持能大大地提高开发效率;最后要注意的是,一般DSP芯片厂商会开放一个技术交流论坛,里面的管理员一般都是DSP芯片厂商的开发工程师,可以以发贴的形式获取他们的技术支持。
" k% x% l; |+ v% z  还有一处资源的来源,就是跟DSP芯片厂商有合作的第三方公司(国内),这类公司跟DSP芯片厂商有很好的接触,一般相关的DSP芯片,他们都会先行做成教育开发板,这点当然主要用于教学,所以他们会有相关的中文资料及相应的demo程序,根据这点,可以很好的借鉴他们的经验及参考他们的资料及程序,其次,他们还会出售自制的仿真器,价格比原厂的会便宜,功能上肯定没有原厂出售的仿真器全面,但足以应对基本的项目开发。
( i/ ~. I6 A0 a# D* k; X  第三处仅供参照,占据国内市场最大的两家DSP厂商TI和ADI在中国都开设的相应级别的DSP培训课程,但费用昂贵,一般都是公司派遣前去学习。2 W, {. R3 I. {4 ~# X1 H4 A
  资源主要包含:, m8 R5 e  S% o5 j) [( q
    Datasheet(数据手册,主要大体介绍一下DSP芯片的功能,内部结构及外设,软件及硬件一些简单介绍,主要作用是可以很快速的了解这款DSP)
( l' J3 M; B4 U/ a    Software Tool Manuals(这个手册主要介绍的DSP时钟、存储器、电源管理等等及所有外设的使用及注意事项,其实就是寄存器的配置,完全可以称之为DSP使用手册)
; ^% [# q% S4 b$ Y    Hardware Tool Manuals(这个手册主要是官方提供的原理图PCB的绘制)、Program Manuals(这个手册主要介绍编译器及内置C库的使用,汇编指令的使用及汇编语法的介绍,官方提供的仿真软件的使用)
0 t3 W  i; N& L# V* [     Engineer to Engineer Note(工程师笔记,这个其实就是DSP芯片自己的工程师在开发这款DSP时所写的笔记,如果你有某个地方未明白,看相应的工程师笔记是最合适的): \8 W* d$ {) }3 i# B
    Program Examples(主要是针对DSP不同的外设,官方提供的程序例子,包含C及汇编)& I' f. |- a: |2 d5 V
  二、官方仿真软件及仿真器的使用(如不使用,可暂时跳过,因为有些DSP可基于开源的操作系统进行开发,例如uClinux)
" t8 ], ^9 R0 u- ^! m$ _2 X  使用仿真软件的方法其实很简单,一般这种软件都设计成类似VC这种,你逐个去试每个菜单下的选项,此时你如配合Examples去使用,更能加深理解,不过我建议,做DSP软件开发,先简单看一下Datasheet、Software Tool Manuals和Program Manuals这三个文档再开始熟悉仿真软件的使用,当然在你熟悉时,肯定需要去不停的再去看这些文档的。仿真器的使用并没有什么需要注意的,一般的仿真器都做了仿呆处理,所以不会插反,仿真器一般都是配合仿真软件使用。(有一点要提醒的是一般DSP开发是基于C语言,如果不会C语言,请先学习C语言)8 J; P0 G( R0 }
  三、DSP最小系统的配置
/ t& y! I6 ^5 h8 [6 ~; R  这部分就正式开始使用DSP了,最小系统主要指DSP的时钟及存储器系统,这时你需要对照着Software Tool Manualsh去仔细看里面的介绍及相关寄存器的配置,结合Examples及Engineer to Engineer Note,如果程序写完后,测试时钟其实很简单,用示波器直接去测量,看测量出来的时钟是否是你配置的那个数,紧接着就是测试存储器,这个测试必须写一段简单的小程序,其实主要就是测试数据总线是否能正常工作,如果在配置最小系统时出现问题,一般问题有二,一是寄存器未正确配置,解决方法是结合Examples及Engineer to Engineer Note仔细看手册,看例程,二是可能开发板上的硬件线路出了问题,解决方法是结合原理图,看线路上是否存在短路的问题,DSP工作电压是否正常等,这步可和硬件工程师一起去查。
- ?; g. {5 T: h9 T  四、DSP外设的使用5 f* H! y9 B1 d8 c! y3 A" T
  其实这部分和配置最小系统一样,只不过某些外设上可能连接了其它的芯片,不同的功能连接的芯片不一样,此时你需要去看这些芯片的资料,然后开始编写代码,然后再测试,测试方法根据不同的功能也会不同,不过DSP开发最常用的就是使用示波器,如有音视频方面的,可借助摄像头,显示屏等等之类的;如中间开发遇到问题,方法还是一样,结合Examples及Engineer to Engineer Note仔细看手册,看例程,有一点要注意,千万不能怀疑不能实现,要对自己有信心。
5 S7 E; v& i- @2 @# V3 G  五、DSP优化* H" j, j4 H3 i* @2 d
  其实到这一步,你已经完全可以使用DSP了,接下来,你需要加深熟悉DSP的整个内部结构,主要包含有几个多少位的MAC,有几个多少位的ALU,有几个多少位的数据寄存器等等,还有外部数据总线上连接了哪些外设,内部数据总线是怎么连接的,并且这些数据总线是多少位,这些在Datasheet会有一张很清楚的DSP结构图,还有DSP的整个Memory Map是怎样的,片上有多少Data Memory,有多少Program Memory等等,了解这些其实就是让你知道DSP的运算性能到底可以达到多少,哪些外设会通过外部数据总线传输数据,DSP内部的寄存器是怎么传输数据的,通过这些可以帮助你解决你在开发中遇到的问题,不过最主要的是帮助你对已经编写完成的代码进行优化,我个人认为的优化方法有以下几种:/ @# @0 w/ y2 Y
  1、一般编写代码首先是用C,基于C层面优化的方法,我如下举例说几种:3 s( J2 E! O5 ~( z$ e
    (1)优化循环
$ T$ x. _; }$ D    for(i = 0;i < max;i ++)
+ A) H, U9 S  b- i     {
; [- b8 g4 y% }, ^  {5 g        for(j = 0; j < max; j ++)/ j  W1 t5 L1 ]9 X. G
        {
# G2 F1 v5 ]. a" R            float sum = 0.0;6 @: b7 n3 }% M8 Q6 ]1 V4 ~
            for(k = 0; k < max; k ++)
) J. c3 Z6 I7 h% g% ~, X+ F            {
; d9 P. h" S+ N. Y- {/ ]# Y& z                sum += input[i * max + k] * input[j * max + k];* E$ x; C% K: y0 _
            }; X, P) T2 P5 D: b, S
            cover[i * max + j] = sum / max;
: q) M' T" I" h. k        }% B" d4 D# x, V+ B; ^" s
    }
# y; ]$ D# v3 e2 b0 O    实例,如input[16] = {1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16},得出的cover如下:, e! I  f( e$ m2 i
     7    17   27   37& O: a2 h1 n7 a3 y: z) I" K
     17  43   69   95% `  F+ u; o" \4 E, k
     27  69  111  153) [, ]5 q2 i3 a8 t( {6 G1 V$ k
     37  95  153  211
* [% E8 h6 ^, X: h2 L, M# I* s    图示:) y: d, Z( E1 R! a& ^4 m* i
    ! y6 y& [  y& [# g  L0 Q9 u
    原理:只需要得到左上角或右上角即可,然后半个矩阵赋值给另半个矩阵即可得到整个矩阵。0 z" M" q6 m6 i- `# i+ X
    算法优化后:# k6 {& a( m# C) M- `0 v# A
    for(i = 0; i < max; i ++)$ Q1 i4 f6 M. c
    {4 C) P4 x- }. `3 m% O8 q
        for(j = i; j < max; j ++)                  // 减少一半循环1 O' |& q) v, M  k8 Y  P
        {
: i  y: S7 y; F2 U! m1 f. f5 t+ T            float sum = 0.0;
( |3 k7 e% B" ~            for(k = 0; k < max; k ++)
/ p8 b7 Q. ~3 M1 @; v0 ^            {
5 O4 A; ^4 P+ N; p7 O                sum += input[i * max + k] * input[j * max + k];
6 g( h- C4 t- F( O            }
8 O" X) m( k- i            cover[i * max + j] = sum / max;* o/ R3 f5 W1 L
            if(i != j)                    // 可加可不加,消除中线上的重复赋值
! Z1 n5 b$ Z  R- g, m7 J, B  d& o            {
& o% z2 X0 ~* p$ V6 U. o                cover[j *max + i] = sum / max;       // 赋值给另半个矩阵# x  b$ a9 G! |, Z
            }
! x2 D' l1 m0 P# E- _  z        }; n9 A8 z/ ]% y+ q4 [8 k
    }
2 r. Y. r5 m6 g& M7 }3 f    (2)条件跳转(使用条件跳转会在流水线中浪费更多的周期)- _' w7 \1 q+ y, }; r; J; j5 P
    k = k -1;
0 S% \( H. ~" U, M- v    if(k < -1)
( g! V! K' o6 P- z: W2 l    {1 O; o3 l! S: D: m5 g2 [
        k = -1;: y$ S" z$ }" i$ y& R) ~( ~
    }
4 O/ I- q4 u( C) j. f1 F    原理:C语言中的max函数在编译的过程中实际上实现的是DSP中的MAX指令。
/ f: s# T9 w  S' c: \& H    优化后:9 B6 A2 H# I( O2 J0 e
    k = max(k-1, -1);9 C/ n) J) `- g8 o5 h# {( R. j0 `
    转换成汇编后:. u1 y& A* X$ r
    R0 += -1;    // R0 == k;4 C" u" B/ D0 ~- S& a$ @; ?
    R1 = -1;
; O% }$ p5 C: I    R0 = MAX(R0, R1);
- J; {7 F3 a: S( R- O5 X# @    (3)for循环中的条件跳转) n) A8 N  y, L
    for
5 a! ~- v/ i0 ~& \! M) J9 D    {
% C# j0 p& f  M) F, V        if{...}else{...}/ D* h: B) ^& f# t
    }# F) `/ ~9 v( l8 c  Q! A$ u. n' C
    原理:减少频繁的条件跳转,当然并不是所有的情况都可以这样做。
+ d6 i( o: w9 d) ?    优化后:6 X; [' u6 F/ r  C' C. ~  I+ j" y
    if; T9 w7 I: I  H/ e) [0 R2 C* ?1 w
    {
8 B( G! b# q4 G        for{...}
- g0 h1 Q2 |2 r8 @2 h0 U2 ^    }  m' |+ S! I* [1 L
    else' W8 J' F7 ?9 ]& J/ @. F
    {. A# h7 I- O# l8 \$ _
        for{...}4 ?$ o( E) c, f" j3 c/ ]3 @
    }
, [8 j+ s  A- q3 T1 ]' f# a  X5 X    (4)使用断言指令来避免条件跳转, M$ G% C- y, o5 z; Y* P& F6 L' F
    if(A)
! r9 c/ {5 g* C- H# D/ M9 U+ o    {
0 V& r" O3 B8 r: v        X = exp1;
6 W$ Y: f7 [& O5 a6 `* U- H+ d     }+ h6 g" o# q, C* L2 K
    else% Q* M4 i3 C( G2 y; {0 L
    {
$ l& k' ~. T- a- u  R3 i4 z        X = exp2;
6 t8 {, ]3 @4 @4 a" e/ w    }    
' R5 s7 }. |  x! c, }  u9 ?    原理:使用断言指令IF(CC) REG = REG,只会消耗一个周期。6 I% p5 G, s  ?( T1 H* q
    优化后:' c) a* k) D7 U) {! I! F8 ^( q
    X = exp1;$ z) a# [- p% `
    if(!A)
! U& T% ]# k4 H" X( ^    {
9 r" A. n! N: M! f. E3 S* y        X = exp2;
% S. D. J  ]" Y3 L+ w    }9 f& x& m+ M& X
    (5)除法(取模)操作0 ]7 x5 y+ [% |, N( @+ f# F
    一般DSP中不支持除法,除法操作是通过仿真的方式来进行实现,有两种,分为低精度和高精度,但都需要相大多的周期。' q) |4 E# J' e0 y
    除数为2的N次方时可采用右移法。
! ]3 L9 V% ?! S/ j6 x4 h    如为提高性能,可采取查表的方式,这样会损失精度。
/ p9 W/ S% ?+ U% X2 J4 i    隐藏的除法:
9 m% ]9 b, G0 w        for(i = start; i < finish; i += step)
7 `' j5 v3 p: J0 \        此时编译器会looper = (finish - start) / step 得到次数。
, k9 t/ h0 R  }1 ~: m) Q    巧妙利用不等式法测:(不过可能会产生溢出,要小心使用)/ t9 s+ G* `' c6 v. d" b2 @0 C
        if(x / y > a / b): T  ^+ X. K' y: u
        可转换为:4 Y4 A3 l% ^+ z' E$ z
        if(x * b  > a * y)
* t, a5 P% s5 J8 w    (6)数据类型1 i( K/ H) X' W
    对于定点DSP而言,对于浮点的操作是用仿真的方式实现的,会消耗很多周期,所以在定点DSP上对于浮点数一般是做定点化的处理,常用的方法我举一个例子:2.5 * a,其实可以转换成80 * a >> 5,不过在定点化时需要注意防溢出。8 @; Z% C8 f* D2 ]8 J
    对于64位数据,也是用仿真的方式实现的,会消耗很多周期。(一般最大仅支持32位数据)" Z5 ^2 Z2 i9 k+ J" ]+ |
    做数字信号处理操作时,如FFT,16bit的操作是比较合适的。2 P: i% F4 @6 J! V4 l2 g
    要做控制类,条件跳转时,32bit的操作是比较合适的。# u, q4 U4 O2 C) F8 A+ _8 ^
    如你的DSP的MAC是16位的,做乘法时,尽量定义成16bit数据。2 U  h; i) n- F( K( J8 W+ ?
    (7)Memory分配4 k3 f; I( [! [: o
    将运算比较频繁的数据和程序段放入片内Memory,开启cache。$ E2 T' Z# p0 }6 k9 Y) F+ t. Q. P
    如DSP能对SDRAM的不同4个bank可以同时访问,此时你可以将需要同时运算的数据放入不同的bank
2 Z2 E$ r) V5 H/ K# Z1 c8 b    (8)开启仿真软件的编译优化选项- N3 z, y: c( S' r! d
    在菜单相应的地方勾上即可,但值得注意时,开启自动编译优化选项后,可能会使执行的结果发生变化,所以需要测试对比一下未开编译优化选项之前的执行结果,一般来说,这个很方便,比较常用。
& d$ r0 J" b/ N8 B$ Y9 _& l    以上8种是我常用到的优化方法,当然基于C层面算法类的优化还有很多种,这个需要慢慢积累,总结一下,一般来说先对C层面进行结构上的优化(上面的1-6均属于),然后进行Memory分配,开启仿真软件的编译优化选项,将运算频繁的程序段用汇编实现,当然如果性能满足要求,就没必要利用汇编了。; A1 _+ r) _6 Z# b& Y
  六、总结- L5 t: Q5 _: t% h4 S
  我认为学习DSP软件开发没有什么捷径,我花了大量的文字在“弄清DSP相关资源的来源及熟读手册”上,实际上是想说,懂得获取资源是很关键的,只有熟悉手册才能完全去使用你所要开发的DSP芯片,其次DSP的主要特点就是高性能,能做一些算法类的运算,所以DSP的优化是相当重要的,关于算法优化的方法有很多种,基本可分为C结构上的优化及利用DSP的特点来进行优化,优化的学习是日易积累的,所以就要多看看相关的资料了。: j( q: ~( B! X+ i$ ?! p
  快速入门的步骤如下:
4 U  C4 e% o6 }. A  F' f) B( p* Z% a  准备一开发板,简单熟悉一下手册及仿真软件,对照着例程看手册,然后再改例程,看是否能按你的意愿去实现,最小系统和每个外设都熟悉一边,恭喜你,你入门了,待续。。。

该用户从未签到

2#
发表于 2016-5-16 13:51 | 只看该作者
楼主很用心啊!+ v! N& x' K+ f
感谢感谢!

该用户从未签到

4#
发表于 2016-6-2 15:28 | 只看该作者
谢谢O(∩_∩)O哈哈~谢谢O(∩_∩)O
您需要登录后才可以回帖 登录 | 注册

本版积分规则

关闭

推荐内容上一条 /1 下一条

EDA365公众号

关于我们|手机版|EDA365电子论坛网 ( 粤ICP备18020198号-1 )

GMT+8, 2025-7-30 16:15 , Processed in 0.109375 second(s), 23 queries , Gzip On.

深圳市墨知创新科技有限公司

地址:深圳市南山区科技生态园2栋A座805 电话:19926409050

快速回复 返回顶部 返回列表