oliglaser
Junior Member level 3
- Joined
- Feb 26, 2010
- Messages
- 31
- Helped
- 0
- Reputation
- 0
- Reaction score
- 0
- Trophy points
- 1,286
- Location
- Manchester, UK
- Activity points
- 1,688
Hi all,
I have recently started with Verilog and FPGAs (I have plenty of experience in most other aspects of electronics though)
I am prototyping a medium speed USB oscilloscope (>50Msps, hopefully up to 250Msps) using an Actel ProASIC3 150k gate device, and a PIC18F which handles the passing of data to the PC ans selecting gain ranges for the opamps etc.
I am using an ABC soft core on the FPGA with a UART to talk to the PIC (easy to use for now whilst learning about things, maybe use SPI or parallel, with a state machine later)
I have manged to get it working at 50Msps, using the above with a dual port RAM. All these are Actel IP cores, but I had to write a Verilog module to generate the addresses for the RAM whilst clocking the ADC (I'm using two clocks, 20MHz for the ABC CPU, and 50MHz for the address generator and ADC clock)
It was a process of trial and error but I managed to get it working and synthesised, but I would like someone to look at the code and pull it to bts, tell me where I could do things better etc. Also it didn't work in simulation (after synthesis, okay before) until I changed the st and rst sensitivities to negedge, which puzzles me - if a signal triggers some action on itself, is the level before or after the edge valid? In books I have seen standard flipflops use posedge signals that operate on them selves but this does not work in my code below..
Anyway, here it is, please feel free to tell me how bad it is
I have recently started with Verilog and FPGAs (I have plenty of experience in most other aspects of electronics though)
I am prototyping a medium speed USB oscilloscope (>50Msps, hopefully up to 250Msps) using an Actel ProASIC3 150k gate device, and a PIC18F which handles the passing of data to the PC ans selecting gain ranges for the opamps etc.
I am using an ABC soft core on the FPGA with a UART to talk to the PIC (easy to use for now whilst learning about things, maybe use SPI or parallel, with a state machine later)
I have manged to get it working at 50Msps, using the above with a dual port RAM. All these are Actel IP cores, but I had to write a Verilog module to generate the addresses for the RAM whilst clocking the ADC (I'm using two clocks, 20MHz for the ABC CPU, and 50MHz for the address generator and ADC clock)
It was a process of trial and error but I managed to get it working and synthesised, but I would like someone to look at the code and pull it to bts, tell me where I could do things better etc. Also it didn't work in simulation (after synthesis, okay before) until I changed the st and rst sensitivities to negedge, which puzzles me - if a signal triggers some action on itself, is the level before or after the edge valid? In books I have seen standard flipflops use posedge signals that operate on them selves but this does not work in my code below..
Anyway, here it is, please feel free to tell me how bad it is
Code:
// AddressGen2.v
module AddressGen2
(
input wire start,
input wire reset,
input wire clk,
output wire[7:0] address
);
reg st;
reg rst;
reg q;
reg [7:0] add;
always @(posedge clk)
begin
st <= start;
if(reset)
begin
if(q)
add <= add + 1;
else
add <= 8'b00000000;
end
else
begin
add <= 8'b00000000;
end
end
always @(posedge clk)
begin
if(add == 8'b11111111)
begin
rst <= 1;
end
else
begin
rst <= 0;
end
end
// q did not work (remained at x) until changed to negedge, but the st needs
// to be at 1 to start the cycle? does it read the level before the edge?
always @(negedge st, negedge rst, posedge reset)
begin
if(reset)
begin
if(st)
q <= 1'b1;
if(rst)
q <= 1'b0;
end
else
q <= 1'b0;
end
assign address = add;
endmodule