Programmable Devices
CPLDs, FPGAs, SoC FPGAs, Configuration, and Transceivers
Announcements
FPGA community forums and blogs have moved to the Altera Community. Existing Intel Community members can sign in with their current credentials.
21618 Discussions

multiple driver error during simulation

Altera_Forum
Honored Contributor II
2,654 Views

Hi 

I am doing a project and am stuck in the synthesis part in Quartus. 

The code was successfully compiled using icarus verilog software.But while compiling the code in Quartus , I get some error messages. 

The code is as follows with its description: 

 

/* 

Whenever positive edge of switch occurs , I need to take the incoming 8 bits (serial inputs on a single pin) and after that I  

have to discard all the bits, until the next posedge of switch. These bits are coming from a parallel in serial out register.  

These bits are stored in a reg called c and i is an integer which keeps the count.  

 

*/ 

module test(si,po,clk,switch,flag); 

input si,clk,switch; 

 

output reg [7:0] po; 

reg [7:0] c,d; 

output reg flag; 

reg count; 

//reg flag; 

integer j,i; 

initial i=0; 

initial flag=0; 

initial count=0; 

always@(posedge clk) 

begin 

if (flag==1) 

begin 

 

c[i]=si; 

i=i+1; 

if(i==8) 

begin 

//count<=1; 

//po<=c; 

po<=(c[7:4]*10)+c[3:0]; 

i=0; 

flag<=0; 

end 

end 

 

end 

 

always@(posedge switch) 

begin 

flag<=1;  

end 

endmodule 

 

The error messges are as follows: 

 

Error: Can't elaborate top-level user hierarchy 

Error (10029): Constant driver at test.v(16) 

Error (10028): Can't resolve multiple constant drivers for net "flag" at test.v(38) 

 

Could anyone help in rectifying the mistake?
0 Kudos
17 Replies
Altera_Forum
Honored Contributor II
1,829 Views

Your flag is driven in two processes. the second process sets it permanently to high... 

You must have a clock input as fast as serial stream (at least) then you run a counter(integer 0 ~ 8) set at zero at MSB or LSB location then increment to 8 and reset zero. 

(vhdl clocked process) --detect edge of switch switch_d <= switch; if switch = '1' and switch_d = '0' then count <= 1; elsif count < 8 then count <= count + 1; end if; if count < 8 then output(count) <= input; end if; if count = 7 then valid <= '1'; else valid <= '0'; end if;
0 Kudos
Altera_Forum
Honored Contributor II
1,829 Views

Hi Kaz 

I have some doubts on your expalaination as follows: 

switch_d <= switch; if switch /= switch_d then count <= 1; else count <= count + 1; end if; 

1)by this are you detecting positive edge of switch 

2) 

output <= input(count); 

what does this do?
0 Kudos
Altera_Forum
Honored Contributor II
1,829 Views

I just corrected the output assignment. 

Yes I detect switch rising level, the count is set to 1 due to one clock latency. 

for safer design you may put this for edge detection: 

if switch = '1' and switch_d = '0' then instead
0 Kudos
Altera_Forum
Honored Contributor II
1,829 Views

 

--- Quote Start ---  

 

(vhdl clocked process) --detect edge of switch switch_d <= switch; if switch = '1' and switch_d = '0' then count <= 1; elsif count < 8 then count <= count + 1; end if; if count < 8 then output(count) <= input; end if; if count = 7 then valid <= '1'; else valid <= '0'; end if;  

--- Quote End ---  

 

As per the specifications the first 8 inputs are to be taken at the positive edge of switch. 

So why do you set count =1 at +ve edge and increase it by 1 when there's no posedge of switch? 

2)  

if count < 8 then output(count) <= input; end if; 

what is this used for?
0 Kudos
Altera_Forum
Honored Contributor II
1,829 Views

You are right, I am still playing with this code for demo only as I am not aware of your inputs behaviour. 

remember you can only detect switch edge one clock period after it rises. 

I am not sure if switch will rise once only or many times.  

 

you can run count 0~7 instead of 0 ~ 8 then it will set back to 0 ready waiting for switch to go up again. 

 

if switch = '1' and switch_d = '0' then 

count <= 1; 

else 

count <= count + 1; -- 0~7 free running 

end if; 

 

output(count) <= input; 

 

...etc.
0 Kudos
Altera_Forum
Honored Contributor II
1,829 Views

 

--- Quote Start ---  

 

I am not sure if switch will rise once only or many times.  

 

 

...etc. 

--- Quote End ---  

 

Yes switch is allowed transitions  

"if switch = '1' and switch_d = '0' then" If I am not wrong this is detecting the positive edge 

So my count needs to be increased only when there is a positive edge and inputs(serial 8 bits) need to be stored in a reg. 

 

Moreover, me being familiar with Verilog, not VHDL, the syntax  

output(count) <= input; 

is troubling me
0 Kudos
Altera_Forum
Honored Contributor II
1,829 Views

if your 8 bits are serial then they can't all come at rising edge of switch but one after the other as per input clock edge otherwise you need to clearify this point. I know RS232 uses no clock. Instead you run a counter to read bits by guess in effect... is that your case as well? is your clock as fast as serial bit stream?

0 Kudos
Altera_Forum
Honored Contributor II
1,828 Views

Do you mean one bit arrives per switch edge?

0 Kudos
Altera_Forum
Honored Contributor II
1,828 Views

Well what I intend to do is that the serial bits are coming at every clock edge(global clock) . i use the switch mechanism to detect that my inputs are stable and I am ready to take the incoming 8 bits serially. So the value of count needs to be increased only when I am taking the inputs. 

Hope this would clarify my specifications.
0 Kudos
Altera_Forum
Honored Contributor II
1,828 Views

 

--- Quote Start ---  

Do you mean one bit arrives per switch edge? 

--- Quote End ---  

 

 

its per clock edge
0 Kudos
Altera_Forum
Honored Contributor II
1,829 Views

The counter is used to move the current input bit to the coorect bit index of output. Thats why I say output(count) <= input i.e.: 

output(0) <= input bit when count = 0 

output(1) <= input bit when count = 1 ...etc. 

 

so count must go up at speed of incoming serial bits.
0 Kudos
Altera_Forum
Honored Contributor II
1,829 Views

Ok well trying out some suggestions, I am here with the final code 

 

 

module test1(si,po,clk,switch,flag); 

input si,clk,switch; 

 

output reg [7:0] po; 

reg [7:0] c,d; 

output reg flag; 

reg check; 

reg count; 

//reg flag; 

integer j,i; 

initial i=0; 

initial flag=0; 

initial count=0; 

always@(posedge clk) 

begin 

if(switch==0) 

check=1; 

if(switch==1 & check==1)  

begin 

check<=0; 

flag<=1; 

end 

 

if (flag==1) 

 

begin 

 

c[i]=si; 

i=i+1; 

///end 

if(i==8) 

begin 

 

po<=(c[7:4]*10)+c[3:0]; 

i=0; 

flag<=0; 

 

end 

end 

 

end 

 

endmodule 

 

Can someone suggest how to optimise this code . I am using a CPLD board which says it requires 94 macrocells for this code but it has got only 64.:)
0 Kudos
Altera_Forum
Honored Contributor II
1,828 Views

aside from resource issue, I think you need a bit more thought on the issue of counting. you need to count 0 ~7 and then freeze on zero until next switch edge.  

One way is this: 

if switch = '1' ... 

count <= 1; 

elsif flag = '1' then 

count <= count + 1; 

end if; 

 

flag <= '1' when count > 0 else '0';
0 Kudos
Altera_Forum
Honored Contributor II
1,828 Views

The multiplier/ adder is going to take too much resource.

0 Kudos
Altera_Forum
Honored Contributor II
1,829 Views

To avoid the multiplier you can use shift and addition for 10 i.e. multiply by 8 using 3 bit shift then multiply by 2 using one bit shift then add products

0 Kudos
Altera_Forum
Honored Contributor II
1,829 Views

Thank You Kaz for the help. 

I am still short of 13 macrocells and also I would like to extend this code for 16 bits instead of 8 bits. 

Any concrete solution?
0 Kudos
Altera_Forum
Honored Contributor II
1,829 Views

I haven't done verilog for ages. I believe your integer (i ) may imply 32 bits in hardware. You only need 3 bits so try constraining that e.g. by using reg.

0 Kudos
Reply