matlabC语言verilog之间的区别.doc_第1页
matlabC语言verilog之间的区别.doc_第2页
matlabC语言verilog之间的区别.doc_第3页
matlabC语言verilog之间的区别.doc_第4页
matlabC语言verilog之间的区别.doc_第5页
已阅读5页,还剩8页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

C语言、verilog与Matlab语言的运算符号的区别C语言verilog Matlab功能描述*,/,+,-乘除一般不能直接写*,/,+,-乘,除,加,减%rem(x,y)取余(在matlab中%表示注释)!(逻辑非)取反即非&逻辑与|逻辑或,=,=,= (=,无右移y?x:y;return(z);function(函数名);Endfunction例:function 7:0 getbyteinput 15:0 addressbegin执行语句;getbyte=result_expresstion;endendfunction说明:1 定义数时至少有一个输入参量2 必须有一条赋值语句给函数中的一个内部变量赋与函数的结果值,该内部变量与函数名相同function out1, out2, . = funname(in1, in2, .)例:function mean,stdev = stat(x)n = length(x);mean = sum(x)/n;stdev=sqrt(sum(x-mean).2/n);function语句assign a = b;连续赋值组合逻辑语言,always外面的赋值语句;always模块里面的阻塞赋值 = 非阻塞赋值 =赋值语句module ( );input ;定义类型output ;reg ; ();(例:dsp i1(.clk(clk) );.clk表示子模块中的名称,(clk)表示本模块中的名称)endmodule一个文件的形式Task endtaskEg:Task and;/定义任务名Input a,b; Output c;BeginC=a+b;Endendtask任务定义wire 组合逻辑数据类型reg 时序逻辑数据类型定义数据类型1、always 语句,连续执行;用于时序逻辑always (posedge clk1 or negedge)边沿(上升沿)触发begin end用于组合逻辑always (a or b)敏感列表 begin end2、initial 语句,只用于测试模块,只执行一次initial begin 语句 end(一个模块中可以有多个initial块,它们都是并行运行的,initial块常用于测试文件虚拟模块。)3、task语句,任务task 模块名;endtask4、function 语句,函数,返回一个表达式的值。function(函数名);endfunction*3、4不常用结构语句可综合的verilog语法子集常用的RTL语法结构如下: 模块声明: moduleendmodule 端口声明:input,output,inout(inout的用法比较特殊,需要注意) 信号类型:wire,reg,tri等,integer常用语for语句中(reg,wire时最常用的,一般tri和integer不用) 参数定义:parameter 运算操作符:各种逻辑操作符、移位操作符、算术操作符大多时可综合的(注:=与!=是不可综合的) 比较判断:ifelse,case(casex,casez)default endcase 连续赋值:assign,问号表达式(?:) always模块:(敏感表可以为电平、沿信号posedge/negedge;通常和连用) beginend(通俗的说,它就是C语言里的 “ ”) 任务定义:taskendtask 循环语句:for(用的也比较少,但是在一些特定的设计中使用它会起到事半功倍的效果) 赋值符号:= 和 = (阻塞和非阻塞赋值,在具体设计中时很有讲究的)可综合的语法时verilog可用语法里很小的一个子集,用最精简的语句描述最复杂的硬件,这也正是硬件描述语言的本质。对于做RTL级设计来说,掌握好上面这些基本语法是很重要。关于C语言的一点总结头文件中常用1 类型定义:typedef(1) 定义一般的类型 例如:typedef int int16;typedef long int32;typedef unsigned int Uint16;typedef unsigned long Uint32;typedef float float32;typedef long double float64;(2)定义结构体为一种数据类型: typedef struct _iq fs; /* Input: sampling frequency (Q15) */ _iq fn; /* Input: the notch frequency (Q15) */ _iq BW; /* the band_width of attenuation by 3DB (Q15) */ _iq b0; /* Output:the coficient of numerator (Q15) */ _iq b1; /* Output:the coficient of numerator (Q15) */ _iq b2; /* Output:the coficient of numerator (Q15) */ _iq a0; /* Output:the coficient of denominator (Q15) */ _iq a1; /* Output:the coficient of denominator (Q15) */ _iq Uk; /* input: the current input of signal */ _iq Uk_1; /* input: the previous input of signal */ _iq Uk_2; /* input: the previous input of signal */ _iq Yk; /* output: the current output of filtered signal */ _iq Yk_1; /* output: the previous output of filtered signal */ _iq Yk_2; /* output: the previous output of filtered signal */ void(*calc)(void*); /* Pointer to the 1st_Lowpass_Filter function */ NF ;NF为一种结构体类型,可以用NF来定义变量;例如: NF nf=NF_initial;/定义一个变量nf,nf为NF类型的,并赋初值。(采用这种方式与直接采用struct的区别是直接用NF,不用带struct, struct的用法见下面) (3)定义一种指向结构体的指针类型 typedef NF *NF_handle; / NF_handle是一种指针类型,void notch_calc(NF_handle);/头文件中的函数申明中,函数notch_calc的输入值是一/个NF型的指针变量;2结构体定义struct(1)先定义结构,再说明结构变量。 如: struct stu int num; char name20; char sex; float score; ; struct stu boy1,boy2; 说明了两个变量 boy1 和boy2为 stu结构类型。也可以用宏定义使一个符号常量来表示一个结构类型。 例如: #define STU struct stu STU boy1,boy2; 这样可以省掉struct(2)在定义结构类型的同时说明结构变量。 例如: struct stu int num; char name 20; char sex; float score; boy1,boy2; 这种形式的说明的一般形式为: struct 结构名 成员表列 变量名表列; (3)直接说明结构变量。 例如: struct int num; char name20; char sex; float score; boy1, boy2; 这种形式的说明的一般形式为: struct 成员表列 变量名表列; (4)定义结构体的位域 struct SCIFFCT_BITS / bits description Uint16 FFTXDLY:8; / 7:0 FIFO transmit delay Uint16 rsvd:5; / 12:8 reserved Uint16 CDC:1; / 13 Auto baud mode enable Uint16 ABDCLR:1; / 14 Auto baud clear Uint16 ABD:1; / 15 Auto baud detect;同位体定义unionunion SCIFFCT_REG Uint16 all; struct SCIFFCT_BITS bit;3 宏定义 #define#define 标识符 字符串 4 文件包含:. 表示跳出该文件夹. 表示本文件夹中例如:#include .includeDSP281x_Device.h 表示DSP281x_Device.h文件在当前位置中的include文件夹中。 .includeDSP281x_Device.h 表示DSP281x_Device.h文件在当前位置外的include文件夹中5 指针的总结 1. 指针是语言中一个重要的组成部分,使用指针编程有以下优点:(1)提高程序的编译效率和执行速度。(2)通过指针可使用主调函数和被调函数之间共享变量或数据结构,便于实现双向数据通讯。(3)可以实现动态的存储分配。(4)便于表示各种数据结构,编写高质量的程序。2. 指针的运算(1)取地址运算符&:求变量的地址(2)取内容运算符*:表示指针所指的变量(3)赋值运算把变量地址赋予指针变量同类型指针变量相互赋值把数组,字符串的首地址赋予指针变量把函数入口地址赋予指针变量(4)加减运算对指向数组,字符串的指针变量可以进行加减运算,如p+n,p-n,p+,p-等。对指向同一数组的两个指针变量可以相减。对指向其它类型的指针变量作加减运算是无意义的。 (5)关系运算指向同一数组的两个指针变量之间可以进行大于、小于、 等于比较运算。指针可与0比较,p=0表示p为空指针。3. 与指针有关的各种说明和意义见下表。int *p; p为指向整型量的指针变量int *pn; p为指针数组,由n个指向整型量的指针元素组成。int (*p)n; p为指向整型二维数组的指针变量,二维数组的列数为nint *p() p为返回指针值的函数,该指针指向整型量int (*p)() p为指向函数的指针,该函数返回整型量int *p p为一个指向另一指针的指针变量,该指针指向一个整型量。4. 有关指针的说明很多是由指针,数组,函数说明组合而成的。但并不是可以任意组合,例如数组不能由函数组成,即数组元素不能是一个函数;函数也不能返回一个数组或返回另一个函数。例如int a5();就是错误的。5. 关于括号在解释组合说明符时, 标识符右边的方括号和圆括号优先于标识符左边的“*”号,而方括号和圆括号以相同的优先级从左到右结合。但可以用圆括号改变约定的结合顺序。6. 阅读组合说明符的规则是“从里向外”。从标识符开始,先看它右边有无方括号或园括号,如有则先作出解释,再看左边有无*号。 如果在任何时候遇到了闭括号,则在继续之前必须用相同的规则处理括号内的内容。例如: int*(*(*a)()10 7 6 4 2 1 3 5上面给出了由内向外的阅读顺序,下面来解释它:(1)标识符a被说明为;(2)一个指针变量,它指向;(3)一个函数,它返回;(4)一个指针,该指针指向;(5)一个有10个元素的数组,其类型为;(6)指针型,它指向;(7)int型数据。因此a是一个函数指针变量,该函数返回的一个指针值又指向一个指针数组,该指针数组的元素指向整型量。因为C语言所有复杂的指针声明,都是由各种声明嵌套构成的。如何解读复杂指针声明呢?右左法则是一个既著名又常用的方法。不过,右左法则其实并不是 C标准里面的内容,它是从C标准的声明规定中归纳出来的方法。C标准的声明规则,是用来解决如何创建声明的,而右左法则是用来解决如何辩识一个声明的,两者可以说是相反的。右左法则:首先从最里面的圆括号看起,然后往右看,再往左看。每当遇到圆括号时,就应该掉转阅读方向。一旦解析完圆括号里面所有的东西,就跳出圆括号。重复这个过程直到整个声明解析完毕。(括号里面从右到左,括号外面从左到右)笔者要对这个法则进行一个小小的修正,应该是从未定义的标识符开始阅读,而不是从括号读起,之所以是未定义的标识符,是因为一个声明里面可能有多个标识符,但未定义的标识符只会有一个。现在通过一些例子来讨论右左法则的应用,先从最简单的开始,逐步加深: int(*func)(int*p);首先找到那个未定义的标识符,就是func,它的外面有一对圆括号,而且左边是一个*号,这说明func是一个指针,然后跳出这个圆括号,先看右边,也是一个圆括号,这说明(*func)是一个函数,而func是一个指向这一类函数的指针,就是一个函数指针,这一类函数具有int*类型的形参,返回值类型是int。int(*func)(int*p,int(*f)(int*);func被一对括号包含,且左边有一个*号,说明func是一个指针,跳出括号,右边也有个括号,那么func是一个指向函数的指针,这类函数具有int*和int(*) (int*)这样的形参,返回值为int类型。再来看一看func的形参int(*f)(int*),类似前面的解释,f也是一个函数指针,指向的函数具有int*类型的形参,返回值为int。int(*func5)(int*p);func右边是一个运算符,说明func是一个具有5个元素的数组,func的左边有一个*,说明func的元素是指针,要注意这里的*不是修饰func的,而是修饰 func5的,原因是运算符优先级比*高,func先跟结合,因此*修饰的是func5。跳出这个括号,看右边,也是一对圆括号,说明 func数组的元素是函数类型的指针,它所指向的函数具有int*类型的形参,返回值类型为int。int(*(*func)5)(int*p);func 被一个圆括号包含,左边又有一个*,那么func是一个指针,跳出括号,右边是一个运算符号,说明func是一个指向数组的指针(一个指针指向数组),现在往左看,左边有一个*号,说明这个数组的元素是指针,再跳出括号,右边又有一个括号,说明这个数组的元素是指向函数的指针。总结一下,就是:func是一个指向数组的指针,这个数组的元素是函数指针,这些指针指向具有int*形参,返回值为int类型的函数。int(*(*func)(int*p)5;func是一个函数指针,这类函数具有int*类型的形参,返回值是指向数组的指针,所指向的数组的元素是具有5个int元素的数组。(疑问:如果 int (*func(int p)5 , 是不是就是一个函数,它的形参是int型的,返回值是一个指向5个元素的数组的指针).要注意有些复杂指针声明是非法的,例如:intfunc(void)5;func是一个返回值为具有5个int元素的数组的函数。但C语言的函数返回值不能为数组,这是因为如果允许函数返回值为数组,那么接收这个数组的内容的东西,也必须是一个数组,但C语言的数组名是一个右值,它不能作为左值来接收另一个数组,因此函数返回值不能为数组。intfunc5(void);func是一个具有5个元素的数组,这个数组的元素都是函数。这也是非法的,因为数组的元素除了类型必须一样外,每个元素所占用的内存空间也必须相同,显然函数是无法达到这个要求的,即使函数的类型一样,但函数所占用的空间通常是不相同的。作为练习,下面列几个复杂指针声明给读者自己来解析。int(*(*func)56)78;(自己给的解答:func是一个指针,它指向一个二维数组,并且这个二维数组的元素是指针,这个指针指向一个二维的int型数组.)int(*(*(*func)(int*)5)(int*);(自己给的解答:func是一个指针,它是一个指向参数为int型指针,返回值是指针的函数指针;这个函数的返回值是指向5个元素的数组的指针,每个元素的指针是一个指向参数为int型指针,返回值是int型的函数指针.)int(*(*func789)(int*)5;(自己给的解答

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论