0
\$\begingroup\$

I'm planning to do a waveform generator using an FPGA board (spartan 6 board from diychips), however I am new to verilog so I am encountering a bit of a problem. I created a sine-wave sequence using MATLAB and imported it into my verilog code. Here's the code that should output the 7 bit sequence :

module dac7bit(input M_CLOCK, output reg [6:0] DAC);
reg[8:0] counter;
reg clk = 0;
reg[4:0] i = 0;

always @(posedge M_CLOCK) begin
    counter <= counter+1;
    if(counter==320)begin
        clk <= ~clk;
        counter <= 0;
    end
end

always @(posedge clk) begin
    case(i)
        5'b00000 :DAC <= 7'b1000000;
        5'b00001 :DAC <= 7'b1001111 ;
        5'b00010 :DAC <= 7'b1011110 ;
        5'b00011 :DAC <= 7'b1101011 ;
        5'b00100 :DAC <= 7'b1110110 ;
        5'b00101 :DAC <= 7'b1111100 ;
        5'b00110 :DAC <= 7'b1111111 ;
        5'b00111 :DAC <= 7'b1111110 ;
        5'b01000 :DAC <= 7'b1111001 ;
        5'b01001 :DAC <= 7'b1110001 ;
        5'b01010 :DAC <= 7'b1100101 ;
        5'b01011 :DAC <= 7'b1010111 ;
        5'b01100 :DAC <= 7'b1001000 ;
        5'b01101 :DAC <= 7'b0110111 ;
        5'b01110 :DAC <= 7'b0101000 ;
        5'b01111 :DAC <= 7'b0011010 ;
        5'b10000 :DAC <= 7'b0001110 ;
        5'b10001 :DAC <= 7'b0000110 ;
        5'b10010 :DAC <= 7'b0000001 ;
        5'b10011 :DAC <= 7'b0000000 ;
        5'b10100 :DAC <= 7'b0000011 ;
        5'b10101 :DAC <= 7'b0001001 ;
        5'b10110 :DAC <= 7'b0010100 ;
        5'b10111 :DAC <= 7'b0100001 ;
        5'b11000 :DAC <= 7'b0110000;
        default: DAC <= 7'b0100000;
    endcase

i<=i+1;
    if(i==24) begin
        i<=0;
    end
end

endmodule

I have created a register DAC that I have mapped in the .ucf file, using this datasheet. The pins are then connected to the R2R DAC outside the board via jumpers. I am not sure if this is the way to do it (to map the pins), I got this idea from how this was done for the I/O board shipped with the FPGA board itself. Here's the .ucf file:

 # DAC
 NET    "DAC<6>" LOC = P104; 
 NET    "DAC<5>" LOC = P101; 
 NET    "DAC<4>" LOC = P99; 
 NET    "DAC<3>" LOC = P97; 
 NET    "DAC<2>" LOC = P94; 
 NET    "DAC<1>" LOC = P92; 
 NET    "DAC<0>" LOC = P87; 

 #====================================================
 # Clock signal 
 NET "M_CLOCK" LOC = P123;

However I could't probe anything, all of the pins were high. I thought that the problem might be with generating my own clock signal, or with the case() syntax, so I tried to just assign some 7 bit value to DAC register on each M_CLOCK cycle. Still, nothing has changed. Therefore I think that the problem is with either initializing the DAC register, mapping it, or assigning values to it, however I can't find anything that could help.

EDIT:

The problem was much more trivial than I expected. It was due to the software I was using. I had installed Xilinx ISE on a Windows 8 machine and some of the features (such as producing working bit .mcs files it would seem) were bugged. Once I got to my school computer that runs a working version of ISE the code worked as expected.

\$\endgroup\$
  • \$\begingroup\$ Were there any warnings or errors produced when you built the design or during programming? What happens if you clock the 2nd always blocks from M_CLOCK instead of clk? \$\endgroup\$ – The Photon Dec 2 '18 at 17:31
  • 1
    \$\begingroup\$ ^^ That and: for the very first Verilog program on an FPGA I recommend a program with : 1 static ON LED, 1 static OFF LED and a 1Hz. blinking LED. \$\endgroup\$ – Oldfart Dec 2 '18 at 17:50
  • \$\begingroup\$ No errors and a warning about truncating a 10 bit value to 9 bit or something similar. Tried running second block from M_CLOCK, still nothing. I did a couple of programs with blinking leds on a I/O board and it worked fine however I didn't change any of the .ucf settings that time. \$\endgroup\$ – Anthropomorphous Dodecahedron Dec 2 '18 at 18:10
  • \$\begingroup\$ Did you look into any waveforms that are generated by you code? \$\endgroup\$ – Ale..chenski Dec 2 '18 at 21:12
  • \$\begingroup\$ Take a look at the RTL (register transfer level) code that is generated by the verilog complier. Typically verilog or vhdl are translated into RTL as a first step, before the implementation-specific bitstream. Maybe there is some constant logic that has been unexpectedly optimized away. \$\endgroup\$ – MarkU Dec 2 '18 at 21:37
3
\$\begingroup\$

This is a very poor code. It has no reset initialization. Your counter[...] is undefined, and thus doesn't increment. So your divider by 320 doesn't run, and the clk is not generated.

Before starting probing anything physically, make a simple testbench, and run ISim (which is a part of Xilinx ISE) on your code. You will see all red signals. Don't bother to implement the code until you see all signals defined and toggling to your ideas.

Something like this:

module test00;

// Inputs
reg M_CLOCK;

// Outputs
wire [6:0] DAC;

// Instantiate the Unit Under Test (UUT)
dac7bit uut ( .M_CLOCK(M_CLOCK), .DAC(DAC) );

initial begin // Initialize Inputs
M_CLOCK = 0;

  // Wait 100 ns for global reset to finish       

#100; // Add stimulus here

end

always begin

 #(100)   M_CLOCK = 1;
 #(100)  M_CLOCK = 0; 

end

endmodule

\$\endgroup\$
1
\$\begingroup\$

I am using Altera, but I think pronciples apply.

Looking into your code I do not think it will not work on real hardware because it is poorly written or has no initialization. When FPGA configures, its registers will anyway power up to at least some logical level, and as it does not matter for your design, so should be no problem.

It sounds like you have problem somewhere else than in this code:

  1. check pin assignment. Did you do it correctly - pin designations are those input and output devices are connected to?
  2. check M_CLOCK clock - is it in there at the pin P123?
  3. what type of DAC is connected? Your code will work properly with R2R DAC not requiring clock, but will not work with any serial DAC chips which require clock and data shift into it.

so I tried to just assign some 7 bit value to DAC register on each M_CLOCK cycle. Still, nothing has changed.

Just assign some 7-bit value to the DAC without using any clock, redefining DAC as wire

module dac7bit(input M_CLOCK, output wire [6:0] DAC);
....
assign DAC[6:0] = 7'b1010101;

and see if it will work with DAC having some voltage output in its output range which would look like this value assigned. If it will not, then your counter code is not a problem, your problem is driving DAC.

By the way, it would be good if you refer to the datasheet of the board/device you are using, as this one (for example) contains 7-segment display at the pin location you think your DAC is in.

\$\endgroup\$
  • \$\begingroup\$ Thanks, I tried to write some value using M_CLOCK, but hadn't thought about "assign", will try it out now. Also, yeah, that is the datasheet I used to assign the pin locations, I will add it to the question. \$\endgroup\$ – Anthropomorphous Dodecahedron Dec 3 '18 at 8:04
  • \$\begingroup\$ What device you use then - as one described in datasheet does NOT state it has DAC at all. You must share datasheet of your board, and ensure it contains devices you want to access in the desired pin locations. \$\endgroup\$ – Anonymous Dec 3 '18 at 8:08
  • \$\begingroup\$ I am using the said device. The DAC is outside the board and is just an R2R ladder connected with jumpers. Since I was not probing the DAC output but the fpga board itself I didn't think to mention it. I will edit it into the question. \$\endgroup\$ – Anthropomorphous Dodecahedron Dec 3 '18 at 8:14
  • \$\begingroup\$ I guess the question is if I can arbitrarily assign some pin numbers to the bits in my DAC register and expect the code to work. I am doing this by altering the .ucf file. Is this the correct way to do it? \$\endgroup\$ – Anthropomorphous Dodecahedron Dec 3 '18 at 8:19
  • \$\begingroup\$ Ok, then the very first step is to probe pins of FPGA at the input to DAC (wihtout DAC connected!) to see that it has binary value you write to it. This way you will know that data reaches output. Finally you can connect LEDs to the pin outputs and run your counter code with very slow clock to see how value changes at the output. \$\endgroup\$ – Anonymous Dec 3 '18 at 8:19

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.