一,首先总结我在网上论坛上发的贴问的问题:
verilog编写的两个奇怪现象:
1.在执行always@(posedge Clk50Mhz or negedge RstN)
if(RstN)
begin
r_State<=4'd0;
r_RxDone<=1'd0;
r_RxData<=8'hff;
end
else if(……)
语句时报错如下:
“cannot match operand(s) in the condition to the corresponding edges in the enclosing event control of the always construct”
开始觉得原因可能是该程序逻辑混乱,既然negedge RstN,则if(RstN)就没意义了。但是我后面有else if语句,即使negedgeRstN后为低,也可以 在else if 的敏感语句中判断出来的啊,况且我的敏感列表中有Clk50Mhz,响应它可以的啊!
2. 在执行always@(posedge Clk50Mhz or negedge RstN)
if(!RstN)
begin
r_State<=4'd0;
r_RxDone<=1'd0;
r_RxData<=8'hff;//控制8个LED灯亮,为高时则亮。
end
对于第一个问题,网上高手说从语义上讲是没有错,但是综合器不能综合这样的语法,属于软件规定的问题。对于第二个问题,网上的人也没有给出我令人满意的答复,他们说是clk没产生之前系统复位了,导致RstN复位。可是我不理解,我的复位时一个io口上的按键,又不是对于系统复位的按键,其怎么可能复位呢?
二.和发送模块一样,也是不能成功接收,我是将接收到的数据用led显示,用串口上位机发送数据,可是最终没有任何效果,且出现了上述所说的第二个问题,基于第二个问题没有解决,所以我也没有深究下去了。
三.下面来贴下我的代码:当然这些代码的编写参考了特权同学黑动力社区的资料
主模块为
module UartReceive(Clk50Mhz,RstN,UartIn,RxData,RxDone);
input Clk50Mhz,RstN,TStart,UartIn;
output RxDone;
output[7:0] RxData;
wire w_SpeedStart;
wire w_ClkBps;
SpeedSet speedset(.Clk50Mhz(Clk50Mhz),.RstN(RstN),.SpeedStart(w_SpeedStart),
.ClkBps(w_ClkBps));
UartReceiveControl uartreceivecontrol(.Clk50Mhz(Clk50Mhz),.RstN(RstN),.ClkBps(w_ClkBps),
.TStart(TStart),.SpeedStart(w_SpeedStart),
.UartIn(UartIn),.RxData(RxData),.RxDone(RxDone));
Endmodule
时钟波特率控制模块为:
module SpeedSet(Clk50Mhz,RstN,Start,ClkBps);
input Clk50Mhz,RstN,Start;
output ClkBps;
reg r_ClkBps;
reg [12:0]ClkCount;
always@(posedge Clk50Mhz or negedge RstN)
if(!RstN)
ClkCount<=1'd0;
else if(ClkCount==13'd5207)
ClkCount<=13'd0;
else if(Start)
ClkCount<=ClkCount+1'd1;
else ClkCount<=1'd0;
assign ClkBps=(ClkCount==13'd2603)?1'd1:1'd0;//generate the 9600bps signal
endmodule
接收控制模块为:
module UartSendContral(Clk50Mhz,RstN,ClkBps,DataIn,Start,TxDone,UartOut);
input Clk50Mhz,RstN,ClkBps,Start;
input[7:0]DataIn;
output TxDone,UartOut;
reg[3:0]State;
reg r_UartOut;
reg r_TxDone;
always@(posedge Clk50Mhz or negedge RstN)
if(!RstN)
begin
State<=4'd0;
r_UartOut<=1'd0;
r_TxDone<=1'd0;
r_UartOut<=1'd1;
end
else if(Start)
case(State) //state machine
4'd0:if(ClkBps)
begin
State<=State+1'd1; //the start of bit
r_UartOut<=1'd0;
end
4'd1,4'd2,4'd3,4'd4,4'd5,4'd6,4'd7,4'd8:if(ClkBps) //the input data
begin
State<=State+1'd1;
r_UartOut<=DataIn[State-1];
end
4'd9,4'd10:if(ClkBps) //two stop bit
begin
State<=State+1'd1;
r_UartOut<=1'd1;
end
4'd11:if(ClkBps) //when it end,it will generate the puls (r_TxDone)
begin
State<=State+1'd1;
r_TxDone<=1'd1;
end
4'd12:if(ClkBps)
begin
State<=1'd0;
r_TxDone<=1'd0;
end
endcase
assign UartOut=r_UartOut;
assign TxDone=r_TxDone;
endmodule
用户377235 2014-2-27 08:53
第一个问题,既然RstN是下降沿触发,说明RstN已经从1变成0,你后面的程序是RstN为1的时候才执行,RstN已经变成0了,所以没办法执行,VHdl和Verilog都是并行执行的,所以你的程序就不会执行了,negedge RstN:必须是if(!RstN),posedge RstN:必须是if(RstN),至于第二个问题,不是很明白你的意思。
用户377235 2011-12-23 20:36
always@(posedge Clk50Mhz or negedge RstN)
应该都是posedge 或者都是negedge
用户377235 2011-12-23 20:36
always@(posedge Clk50Mhz or negedge RstN)
应该都是posedge 或者都是negedge