问题:开发板上电后,串口一直发数据。
解决方式:将电平触发改为边沿触发。
Error (10327): VHDL error at top.vhd(113): can’t determine definition of operator “”=“” – found 3 possible definitions
中文:无法确定运算符“” =“的定义-找到3个可能的定义
错误代码
解决方式:去掉std_logic类型数专用的双引号”“。
Error (10028): Can’t resolve multiple constant drivers for net “rev_ready” at top.vhd(89)
错误(10028):无法解析top.vhd(89)的网络“ rev_ready”的多个常量驱动程序
原因:在多个进程中,给一个信号赋值,那么这个信号到底是多少没法确定,所以去掉其他进程中的赋值。
常见问题:改变输出信号的值
再建一个子模块或process,定义一对新的输入、输出信号。新输入信号接收输出信号的值,几个时钟计数(或其他条件)之后,给新输出信号赋值。
Error (10822): HDL error at top.vhd(119): couldn’t implement registers for assignments on this clock edge
在这个时钟边缘,不能给寄存器赋值。
解决办法:rising_edge()在进程中只能使用一次。而且在一个“IF”语句中不能有else。而且一定要在进程的最外层。如下图所示。
Error (10028): Can’t resolve multiple constant drivers for net usartTransferRequestOut" at top.vhd(191)
不能解析usartTransferRequestOut信号的多个常量驱动。
意思是有多个进程使用都给一个信号赋值了。不能同时给一个信号赋值导致数据共享困难。
警告:如果没有时序驱动,那么电路就成了组合逻辑电路了,会报警告。
术语 :“可综合”和“不可综合”
可综合:可以生成实际电路的。不可综合与其相反,即不能生成实际电路的,通常用于测试文件。
术语:封装 模型中封装可重用代码的一种方法。是在整个模型中存储并使用信息的最方便的方式。VHDL有两个内置封装,即为“标准”和“TEXTIO”。
关键字:package
封装包括:
- 封装声明(需要)
类型声明
子程序声明 - 封装题(可选)
子程序定义
术语:库: 含有封装或者封装集。
包括
资源库
- 标准封装
- IEEE开发的封装
- ALTERA组件封装
- 设计中 所引用的任意设计单元库
工作库 - 单元所编译的库
线连接的关系是可以1对多但不可以多对1
原因:因为cpld是并行执行的,所以如果多对1的话,当前时刻这个wire的值是多少无法确定。
wire 和reg 的区别
字面理解,线型和寄存器型。
数据保存的区别:线型表示直连,即输入有变化,输出立即有变化。寄存器型能保持其值不改变直到触发条件发生。
使用场景
定义端口时:input 、inout只能使用wire型,output 可以使用wire 或 reg.定义对外信号时,默认是wire型,定义内部信号时,必须声明是什么型。
赋值使用时:wire只能用在assign 赋值,reg只能用在initial和always环境中。
阻塞(block)/非阻塞性赋值
阻塞赋值:可以认为只有1个步骤的操作,即计算RHS(右手侧,表达式右边)并更新LHS,强调计算、更新两个动作同时性,是一个操作.
非阻塞赋值:每个时钟上升沿计算、更新一次。所以这种n个变量连续传递的数据会有n个时钟延时。
CPLD资源消耗:CPLD中“==”全等比较非常耗费资源,因此尽量少用。
module参数传递:
1、module_name #( parameter1, parameter2) inst_name( port_map);
2、module_name #( .parameter_name(para_value), .parameter_name(para_value)) inst_name (port map);
inout用法:
默认状态是输出状态,如果需要将输出转换为输入,需要首先将其配置为高阻状态,然后再读取。
组合逻辑应该做的事情
1、取脉冲。
2、状态转换。
Warning (21074): Design contains 4 input pin(s) that do not drive logic
** Warning (15610): No output dependent on input pin “sys_clk”**
** Warning (15610): No output dependent on input pin “sys_rst_n”**
警告:没有输出依赖这两个输入引脚,通常是程序错误造成的。程序错误多种多样,可以阻塞赋值改非阻塞赋值或者其他。。
always块中语句执行时间:一次触发条件满足,所有符合条件的语句都会执行一遍,其实就是某一条符合条件的电路通了。这个特点决定了在边沿触发的时序逻辑电路中,不适合用阻塞赋值,使用阻塞赋值可能会导致无法预料的错误或不可综合。阻塞赋值的特点是执行完某条语句之前,后面的语句不能执行,和always块的执行逻辑有冲突的地方。阻塞赋值一般用在组合逻辑电路。
串口调试输出丢数据 SPI的速度太快,串口没来的及发送之前的数据,新的数据又来了,所以会丢失。
verilog数据发送方法:数据更新和发送标志同时更新,下个时刻发送标志关闭,可以保证数据发送一次且发送正确。
连续赋值情况避免:在verilog中,一定要注意连续赋值,可能会出现数据更新不及时的情况。导致这种情况的原因是非阻塞性赋值,数据会在块结束后更新数据。举例如下:会导致地址没有生效,发送暂存字节会拿到一个不是上面计算出地址的数据。
address <= spi_recv_data[6:1]; // 取接收地址;
send_byte_temp <= time_register[address ]; // 发送数据更新
spi_send_status <= 1'd1; // 启动发送
st_done <= 1'b1; // 该状态下处理完毕
注意信号的同时性 :比如赋值和启动同时进行。
begin…end语句之间连续多条语句给某个寄存器赋值:尽量避免这种写法,可能会导致不可预知的错误。
FPGA 引脚模式:如果选择LVCOMS可能会报警告,警告不能消除。
verilog 清0操作:清零操作可能会有中间值,可能会触发‘>’或‘<’号。
统一条件下不要对某个变量多次赋值 : 这样最后让逻辑变得混乱。例如下,在一个begin 里面,多次对ctrl_reg_temp赋值。
#
NIOS II 是什么?
NIOS II 是FPGA 把没有利用的逻辑单元做成了一个小的MCU单元,从而不需要再外接一个MCU。NIOS 核调用各个IP核。
IP软核是什么
IP软核是altera 已经定义好的逻辑块,省的自己浪费时间写了,如PLL IP核,USART IP 核,定时器IP核,SDRAM IP核等。