"Hello World" equivalent for hardware engineers
Blog Post
Posted Jul 8, 2009
by Dan Gardner
Follow on Twitter
Go URL
What is a Go URL?I was staring out my office window at some towering Douglas fir trees, trying to figure out how to introduce non-DSP hardware engineers to how cool C synthesis is. Okay, I did say engineers since a majority of people would not find anything to do with C or synthesis cool. I’m sure I’d get a lot more Google hits on my blog if I talked about the Dallas Cowboys or the Portland Trailblazers, my big interests outside of work and family.
Anyway, back to my dilemma. The first adopters of C synthesis have been mostly DSP gurus developing wireless or video hardware, so you see a lot of FIR filter demos that show how you can get lots of different implementations from the same C code simply by adjusting the loop constraints for latency and throughput. What about someone coming from a pure RTL background that is writing non-DSP ASIC or FPGA hardware. How can I show them something quick and easy that anyone can try?
Preparing RecommendationsI drifted back to when I was first starting at Lattice Semiconductor in the mid-90s. VHDL was just making its way into programmable logic. Schematics were losing out to ABEL for the simple PLDs, but the CPLD and FPGA devices needed something more abstract. Yeah, I know, I’m dating myself. Anyway, our basic training for new field application engineers was based around building a clock dividing counter and driving some seven segment LEDs on a demo board. There, I have it. The first test of a hardware synthesis tool is to make some LEDs blink on a demo board. This would be the equivalent of writing C code to print out “Hello World” for the first time coder.
As a second check, one of my standard questions during job interviews to get a baseline for someone’s hardware knowledge was to have them design a simple binary up counter with asynchronous reset. That’s about as basic a hardware problem as you can get, but it uncovered whether someone understood synthesis or just the language semantics. Of course, if you didn’t write VHDL everyday, remembering the library use statements with the standard IEEE synthesis libraries was hard to fake. Modeling the reset and clock with the proper sensitivity list was pretty straightforward. However, the counter registers were read and written, so the common mistake of declaring them as outputs on the interface caused an error unless you used internal signals. I expected them to write something like:
LIBRARY ieee;
USE ieee.std_logic_1164.all;
USE ieee.std_logic_unsigned.all;
ENTITY cnt IS
PORT (
clk : IN STD_LOGIC;
rst : IN STD_LOGIC;
qout : OUT STD_LOGIC);
END cnt;
ARCHITECTURE rtl OF cnt IS
SIGNAL cnt_reg : STD_LOGIC_VECTOR(15 downto 0);
BEGIN
PROCESS (clk, rst)
BEGIN
IF rst = ‘0′ THEN
cnt_reg <= (others => ‘0′);
ELSIF (rising_edge(clk)) THEN
cnt_reg <= cnt_reg + ‘1′;
END IF;
END PROCESS;
qout <= cnt_reg(15);
END rtl;
Now, you can pass that part of the interview, but I digress. Back to using C for hardware design… I happened to have an older Altera NIOS II Development Kit with a Stratix II FPGA, some LEDs and buttons on it. After downloading the correct reference manual, I had pinouts for the devices on the board. You have to love the new BlackBerry Pearl with built in camera for stuff just like this blog.

This should be pretty easy to do. The crystal oscillator is running at 50MHz, so I decided to blink an LED every second with a 50/50 duty cycle. The first step is to write a C program to do this function. Basically, I just want to toggle the LED value every 25M clock cycles to have it blink once per second (on for half a second, off for half a second).
#define MAX_COUNT 50000000
bool clk_div()
{
static bool toggle_val=false;
for (int i=0; i
if (i==MAX_COUNT/2-1)
toggle_val = !toggle_val;
}
return toggle_val;
}
The static statement creates the register that will drive the LED. This program will compile with any C compiler. On Windows, I use the free Microsoft Visual C++ Express version. On Linux, gcc is most common.
A simple testbench will show that it is working in the debugger:
#include
bool clk_div();
int main()
{
printf(”Starting clock divider\n”);
for (int i=0; i<9; i++)
{
printf(”Clock value = %i\n”, clk_div());
}
return 0;
}

Now, I’m ready to synthesize this down to the board and see if it works as I expect. A common question that comes up from hardware designers is “how do I control the size of the registers?” Remember, the VHDL for the counter defined std_logic and std_logic_vector types. In this case, the static bool toggle can obviously be implemented as a single bit. The loop counter “i” needs to hold MAX_COUNT/2-1, so for the 50MHz clock, this is a 25-bit unsigned number. The standard C int data type is at least 32-bits, so it can hold this number, but I can model this exactly in C and test it using the Mentor Graphics Algorithmic Datatypes, a free download from http://www.mentor.com/products/esl/high_level_synthesis/ac_datatypes.
By replacing the definition of the loop variable to a uint25, I’m guaranteed to use a 25-bit unsigned number and see that it still works. Better yet, I can try a uint24 and see that the loop never makes it to MAX_COUNT/2-1. I just have to include “ac_int.h” and change the for loop to:
for (uint25 i=0; i
To synthesize this design, I bring up Catapult C Synthesis, add the input file to the project, set up the clock at 50MHz, enable active low asynchronous reset and set the technology to an Altera EP2S60F672C-3. To tell Catapult that I want this design to be free running, I pipeline the top-level design with an initiation interval of 1 (II=1). Then, I generate RTL (VHDL or Verilog). After running through Precision RTL and Altera Quartus, I have a bitstream I can program onto the board.
Voila – I have a blinking LED and reset from a push button. If you have QuickTime, you can watch the 8 second video I took, again with my BlackBerry, of my board blinking (blinking_led.3GP). Unfortunately, I can’t seem to include the video as an attachment in this post. Here’s link to it on YouTube, http://www.youtube.com/watch?v=mNKEvC8P3Zc.
Thanks for reading. Comments and questions welcome.
Dan
More Blog Posts
Preparing RecommendationsRecent Posts
- Mentor ESL in TSMC Reference Flow 12
- 48th DAC - Gary’s Magic Formula
- DAC: 9th ESL Symposium
- HLS Fundamentals / Part 2
- HLS Fundamentals: Loop Unrolling and Loop Pipelining
- HLS Contest: And the winner is...
- A Designer’s Perspective on ESL Methodologies for an OFDM Modem Design
- Catapult C and the 7 Samuraïs
- The Why, What and How of HLS @ DATE 2011
- DVCon: Wally Rhine's Keynote
Comments (↓ Add Your Own)
12 Comments on this Post
Commented on 10:57 PM, Jul 8, 2009
By Din
Commented on 4:14 PM, Jul 15, 2009
By Vova
Commented on 12:36 AM, Jul 16, 2009
By Dan Gardner
Commented on 11:38 PM, Jul 22, 2009
By Hardware Engineers need to Communicate « Dan Gardner’s Blog
Commented on 7:05 PM, Aug 28, 2009
By Ramping up with C Synthesis: practical learning resources « Thomas Bollaert’s Blog
Commented on 5:38 PM, Oct 1, 2009
By Cpr
Commented on 11:46 PM, Oct 1, 2009
By Dan Gardner
Commented on 10:37 PM, Feb 17, 2010
By Janarbek Matai
Commented on 11:54 PM, Feb 17, 2010
By Janarbek Matai
Commented on 12:11 AM, Feb 18, 2010
By Dan Gardner
Commented on 2:02 AM, Feb 20, 2010
By Janarbek Matai
Commented on 11:53 PM, Feb 20, 2010
By Dan Gardner
Add Your Comment
Please complete the following information to comment or sign in.