EDN首页   博客首页 用户登陆  |  注册
aaa
发表于 2009/12/7 10:42:48

0

关于投票

(转载) 如何在Nios II顯示8位數的七段顯示器? (IC Design) (DE2) (Nio

之前討論用硬體Verilog顯示8位數的七段顯示器,本文要討論在Nios II用軟體C語言控制8位數的七段顯示器。

Introduction
使用環境:Quartus II 7.2 SP1 + Nios II EDS 7.2 SP1 + DE2(Cyclone II EP2C35F627C6)

(原創) 如何顯示8位數的七段顯示器? (IC Design) (Verilog) (DE2)曾經討論過用硬體Verilog顯示8位數的七段顯示器,今天剛好有需要想在Nios II從軟體C語言去控制七段顯示器,本來想自己寫一個custom component,後來發現友晶的NIOS II Reference Design已經寫好了,只要會『用』就好了。

Nios II的Reference Design放在DE2 CD中的\DE2_demonstrations\SOPC_Builder\Reference_Design\下,(或從http://www.terasic.com/downloads/cd-rom/de2/ 下載),若你想自己從頭到尾自己由SOPC Builder建立,請參閱(原創) 如何自己用SOPC Builder建立一個能在DE2上跑μC/OS-II的Nios II系統? (IC Design) (DE2) (Quartus II) (Nios II) (SOPC Builder) (μC/OS-II)

C語言  / hello_world.c

 1 /* 
 2 (C) OOMusou 2008 http://oomusou.cnblogs.com
 3 
 4 Filename    : hello_world.c
 5 Compiler    : Nios II gcc
 6 Description : Demo how to display 7 seg.
 7 Release     : 04/27/2008 1.0
 8 */
 9 #include <stdio.h>
10 #include "system.h"
11 #include "basic_io.h"
12 
13 int main() {
14   int i;
15   for(i = 0; i != 100; i++)  {
16     Sleep(1);
17     seg7_show(SEG7_DISPLAY_BASE, i);
18   }
19 }
20 


你一定會問我,怎麼知道seg7_show()這個API可以在Nios II使用?我是在SEG7_LUT_8這個目錄下的inc\basic_io.h知道的,因為一個custom component一定會有一個include檔定義軟體能用的API。

C語言 / basic_io.h

 1 #ifndef   __basic_io_H__
 2 #define   __basic_io_H__
 3 
 4 #include <io.h>
 5 #include <stdio.h>
 6 #include <unistd.h>
 7 #include <stdlib.h>
 8 #include "system.h"
 9 #include "sys/alt_irq.h"
10 
11 //  for GPIO
12 #define inport(base)                                  IORD(base, 0) 
13 #define outport(base, data)                           IOWR(base, 0, data)
14 #define get_pio_dir(base)                             IORD(base, 1) 
15 #define set_pio_dir(base, data)                       IOWR(base, 1, data)
16 #define get_pio_irq_mask(base)                        IORD(base, 2) 
17 #define set_pio_irq_mask(base, data)                  IOWR(base, 2, data)
18 #define get_pio_edge_cap(base)                        IORD(base, 3) 
19 #define set_pio_edge_cap(base, data)                  IOWR(base, 3, data)
20 
21 //  for SEG7 Display
22 #define seg7_show(base,data)                          IOWR(base, 0, data)
23 
24 //  for Time Delay
25 #define msleep(msec)                                  usleep(1000*msec);
26 #define Sleep(sec)                                    msleep(1000*sec);
27 
28 #endif


21行

//  for SEG7 Display
#define seg7_show(base,data)                          IOWR(base, 0, data)


我們發現了seg7_show()這個巨集,所以知道用這個巨集可以控制七段顯示器。

問題又來了,他要我們傳入七段顯示器的base address,我們要怎麼知道呢?

在SOPC Builder會分配每個component的base address,Nios II EDS在產生system library時,會將所有的address定義在\software\hello_world_0_syslib\Debug\system_description\system.h下。

C語言 / system.h

  1 /* system.h
  2  *
  3  * Machine generated for a CPU named "cpu_0" as defined in:
  4  * c:\0Clare\DE2\switch_seg7_ip\software\hello_world_0_syslib\..\..\system_0.ptf
  5  *
  6  * Generated: 2008-04-27 00:14:19.203
  7  *
  8  */
  9 
 10 #ifndef __SYSTEM_H_
 11 #define __SYSTEM_H_
 12 
 13 /*
 14 
 15 DO NOT MODIFY THIS FILE
 16 
 17    Changing this file will have subtle consequences
 18    which will almost certainly lead to a nonfunctioning
 19    system. If you do modify this file, be aware that your
 20    changes will be overwritten and lost when this file
 21    is generated again.
 22 
 23 DO NOT MODIFY THIS FILE
 24 
 25 */
 26 
 27 /******************************************************************************
 28 *                                                                             *
 29 * License Agreement                                                           *
 30 *                                                                             *
 31 * Copyright (c) 2003 Altera Corporation, San Jose, California, USA.           *
 32 * All rights reserved.                                                        *
 33 *                                                                             *
 34 * Permission is hereby granted, free of charge, to any person obtaining a     *
 35 * copy of this software and associated documentation files (the "Software"),  *
 36 * to deal in the Software without restriction, including without limitation   *
 37 * the rights to use, copy, modify, merge, publish, distribute, sublicense,    *
 38 * and/or sell copies of the Software, and to permit persons to whom the       *
 39 * Software is furnished to do so, subject to the following conditions:        *
 40 *                                                                             *
 41 * The above copyright notice and this permission notice shall be included in  *
 42 * all copies or substantial portions of the Software.                         *
 43 *                                                                             *
 44 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR  *
 45 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,    *
 46 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE *
 47 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER      *
 48 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING     *
 49 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER         *
 50 * DEALINGS IN THE SOFTWARE.                                                   *
 51 *                                                                             *
 52 * This agreement shall be governed in all respects by the laws of the State   *
 53 * of California and by the laws of the United States of America.              *
 54 *                                                                             *
 55 ******************************************************************************/
 56 
 57 /*
 58  * system configuration
 59  *
 60  */
 61 
 62 #define ALT_SYSTEM_NAME "system_0"
 63 #define ALT_CPU_NAME "cpu_0"
 64 #define ALT_CPU_ARCHITECTURE "altera_nios2"
 65 #define ALT_DEVICE_FAMILY "CYCLONEII"
 66 #define ALT_STDIN "/dev/jtag_uart_0"
 67 #define ALT_STDIN_TYPE "altera_avalon_jtag_uart"
 68 #define ALT_STDIN_BASE 0x006810f0
 69 #define ALT_STDIN_DEV jtag_uart_0
 70 #define ALT_STDIN_PRESENT
 71 #define ALT_STDOUT "/dev/jtag_uart_0"
 72 #define ALT_STDOUT_TYPE "altera_avalon_jtag_uart"
 73 #define ALT_STDOUT_BASE 0x006810f0
 74 #define ALT_STDOUT_DEV jtag_uart_0
 75 #define ALT_STDOUT_PRESENT
 76 #define ALT_STDERR "/dev/jtag_uart_0"
 77 #define ALT_STDERR_TYPE "altera_avalon_jtag_uart"
 78 #define ALT_STDERR_BASE 0x006810f0
 79 #define ALT_STDERR_DEV jtag_uart_0
 80 #define ALT_STDERR_PRESENT
 81 #define ALT_CPU_FREQ 100000000
 82 #define ALT_IRQ_BASE NULL
 83 
 84 /*
 85  * processor configuration
 86  *
 87  */
 88 
 89 #define NIOS2_CPU_IMPLEMENTATION "fast"
 90 #define NIOS2_BIG_ENDIAN 0
 91 
 92 #define NIOS2_ICACHE_SIZE 4096
 93 #define NIOS2_DCACHE_SIZE 2048
 94 #define NIOS2_ICACHE_LINE_SIZE 32
 95 #define NIOS2_ICACHE_LINE_SIZE_LOG2 5
 96 #define NIOS2_DCACHE_LINE_SIZE 4
 97 #define NIOS2_DCACHE_LINE_SIZE_LOG2 2
 98 #define NIOS2_FLUSHDA_SUPPORTED
 99 
100 #define NIOS2_EXCEPTION_ADDR 0x00800020
101 #define NIOS2_RESET_ADDR 0x00000000
102 #define NIOS2_BREAK_ADDR 0x00680020
103 
104 #define NIOS2_HAS_DEBUG_STUB
105 
106 #define NIOS2_CPU_ID_SIZE 1
107 #define NIOS2_CPU_ID_VALUE 0
108 
109 /*
110  * A define for each class of peripheral
111  *
112  */
113 
114 #define __ALTERA_AVALON_TRI_STATE_BRIDGE
115 #define __ALTERA_AVALON_CFI_FLASH
116 #define __ALTERA_AVALON_NEW_SDRAM_CONTROLLER
117 #define __ALTERA_AVALON_EPCS_FLASH_CONTROLLER
118 #define __ALTERA_AVALON_JTAG_UART
119 #define __ALTERA_AVALON_UART
120 #define __ALTERA_AVALON_TIMER
121 #define __ALTERA_AVALON_LCD_16207
122 #define __ALTERA_AVALON_PIO
123 #define __SEG7_LUT_8
124 #define __SRAM_16BIT_512K
125 #define __DM9000A
126 #define __ISP1362
127 #define __BINARY_VGA_CONTROLLER
128 #define __AUDIO_DAC_FIFO
129 
130 /*
131  * tri_state_bridge_0 configuration
132  *
133  */
134 
135 #define TRI_STATE_BRIDGE_0_NAME "/dev/tri_state_bridge_0"
136 #define TRI_STATE_BRIDGE_0_TYPE "altera_avalon_tri_state_bridge"
137 #define ALT_MODULE_CLASS_tri_state_bridge_0 altera_avalon_tri_state_bridge
138 
139 /*
140  * cfi_flash_0 configuration
141  *
142  */
143 
144 #define CFI_FLASH_0_NAME "/dev/cfi_flash_0"
145 #define CFI_FLASH_0_TYPE "altera_avalon_cfi_flash"
146 #define CFI_FLASH_0_BASE 0x00000000
147 #define CFI_FLASH_0_SPAN 4194304
148 #define CFI_FLASH_0_SETUP_VALUE 40
149 #define CFI_FLASH_0_WAIT_VALUE 160
150 #define CFI_FLASH_0_HOLD_VALUE 40
151 #define CFI_FLASH_0_TIMING_UNITS "ns"
152 #define CFI_FLASH_0_UNIT_MULTIPLIER 1
153 #define CFI_FLASH_0_SIZE 4194304
154 #define ALT_MODULE_CLASS_cfi_flash_0 altera_avalon_cfi_flash
155 
156 /*
157  * sdram_0 configuration
158  *
159  */
160 
161 #define SDRAM_0_NAME "/dev/sdram_0"
162 #define SDRAM_0_TYPE "altera_avalon_new_sdram_controller"
163 #define SDRAM_0_BASE 0x00800000
164 #define SDRAM_0_SPAN 8388608
165 #define SDRAM_0_REGISTER_DATA_IN 1
166 #define SDRAM_0_SIM_MODEL_BASE 1
167 #define SDRAM_0_SDRAM_DATA_WIDTH 16
168 #define SDRAM_0_SDRAM_ADDR_WIDTH 12
169 #define SDRAM_0_SDRAM_ROW_WIDTH 12
170 #define SDRAM_0_SDRAM_COL_WIDTH 8
171 #define SDRAM_0_SDRAM_NUM_CHIPSELECTS 1
172 #define SDRAM_0_SDRAM_NUM_BANKS 4
173 #define SDRAM_0_REFRESH_PERIOD 15.625
174 #define SDRAM_0_POWERUP_DELAY 100.0
175 #define SDRAM_0_CAS_LATENCY 3
176 #define SDRAM_0_T_RFC 70.0
177 #define SDRAM_0_T_RP 20.0
178 #define SDRAM_0_T_MRD 3
179 #define SDRAM_0_T_RCD 20.0
180 #define SDRAM_0_T_AC 5.5
181 #define SDRAM_0_T_WR 14.0
182 #define SDRAM_0_INIT_REFRESH_COMMANDS 2
183 #define SDRAM_0_INIT_NOP_DELAY 0.0
184 #define SDRAM_0_SHARED_DATA 0
185 #define SDRAM_0_SDRAM_BANK_WIDTH 2
186 #define SDRAM_0_TRISTATE_BRIDGE_SLAVE ""
187 #define SDRAM_0_STARVATION_INDICATOR 0
188 #define SDRAM_0_IS_INITIALIZED 1
189 #define ALT_MODULE_CLASS_sdram_0 altera_avalon_new_sdram_controller
190 
191 /*
192  * epcs_controller configuration
193  *
194  */
195 
196 #define EPCS_CONTROLLER_NAME "/dev/epcs_controller"
197 #define EPCS_CONTROLLER_TYPE "altera_avalon_epcs_flash_controller"
198 #define EPCS_CONTROLLER_BASE 0x00680800
199 #define EPCS_CONTROLLER_SPAN 2048
200 #define EPCS_CONTROLLER_IRQ 0
201 #define EPCS_CONTROLLER_DATABITS 8
202 #define EPCS_CONTROLLER_TARGETCLOCK 20
203 #define EPCS_CONTROLLER_CLOCKUNITS "MHz"
204 #define EPCS_CONTROLLER_CLOCKMULT 1000000
205 #define EPCS_CONTROLLER_NUMSLAVES 1
206 #define EPCS_CONTROLLER_ISMASTER 1
207 #define EPCS_CONTROLLER_CLOCKPOLARITY 0
208 #define EPCS_CONTROLLER_CLOCKPHASE 0
209 #define EPCS_CONTROLLER_LSBFIRST 0
210 #define EPCS_CONTROLLER_EXTRADELAY 0
211 #define EPCS_CONTROLLER_TARGETSSDELAY 100
212 #define EPCS_CONTROLLER_DELAYUNITS "us"
213 #define EPCS_CONTROLLER_DELAYMULT "1e-006"
214 #define EPCS_CONTROLLER_PREFIX "epcs_"
215 #define EPCS_CONTROLLER_REGISTER_OFFSET 0x200
216 #define EPCS_CONTROLLER_USE_ASMI_ATOM 1
217 #define EPCS_CONTROLLER_CLOCKUNIT "kHz"
218 #define EPCS_CONTROLLER_DELAYUNIT "us"
219 #define ALT_MODULE_CLASS_epcs_controller altera_avalon_epcs_flash_controller
220 
221 /*
222  * jtag_uart_0 configuration
223  *
224  */
225 
226 #define JTAG_UART_0_NAME "/dev/jtag_uart_0"
227 #define JTAG_UART_0_TYPE "altera_avalon_jtag_uart"
228 #define JTAG_UART_0_BASE 0x006810f0
229 #define JTAG_UART_0_SPAN 8
230 #define JTAG_UART_0_IRQ 1
231 #define JTAG_UART_0_WRITE_DEPTH 64
232 #define JTAG_UART_0_READ_DEPTH 64
233 #define JTAG_UART_0_WRITE_THRESHOLD 8
234 #define JTAG_UART_0_READ_THRESHOLD 8
235 #define JTAG_UART_0_READ_CHAR_STREAM ""
236 #define JTAG_UART_0_SHOWASCII 1
237 #define JTAG_UART_0_READ_LE 0
238 #define JTAG_UART_0_WRITE_LE 0
239 #define JTAG_UART_0_ALTERA_SHOW_UNRELEASED_JTAG_UART_FEATURES 0
240 #define ALT_MODULE_CLASS_jtag_uart_0 altera_avalon_jtag_uart
241 
242 /*
243  * uart_0 configuration
244  *
245  */
246 
247 #define UART_0_NAME "/dev/uart_0"
248 #define UART_0_TYPE "altera_avalon_uart"
249 #define UART_0_BASE 0x00681000
250 #define UART_0_SPAN 32
251 #define UART_0_IRQ 2
252 #define UART_0_BAUD 115200
253 #define UART_0_DATA_BITS 8
254 #define UART_0_FIXED_BAUD 1
255 #define UART_0_PARITY 'N'
256 #define UART_0_STOP_BITS 1
257 #define UART_0_USE_CTS_RTS 0
258 #define UART_0_USE_EOP_REGISTER 0
259 #define UART_0_SIM_TRUE_BAUD 0
260 #define UART_0_SIM_CHAR_STREAM ""
261 #define UART_0_FREQ 100000000
262 #define ALT_MODULE_CLASS_uart_0 altera_avalon_uart
263 
264 /*
265  * timer_0 configuration
266  *
267  */
268 
269 #define TIMER_0_NAME "/dev/timer_0"
270 #define TIMER_0_TYPE "altera_avalon_timer"
271 #define TIMER_0_BASE 0x00681020
272 #define TIMER_0_SPAN 32
273 #define TIMER_0_IRQ 3
274 #define TIMER_0_ALWAYS_RUN 0
275 #define TIMER_0_FIXED_PERIOD 0
276 #define TIMER_0_SNAPSHOT 1
277 #define TIMER_0_PERIOD 1.0
278 #define TIMER_0_PERIOD_UNITS "ms"
279 #define TIMER_0_RESET_OUTPUT 0
280 #define TIMER_0_TIMEOUT_PULSE_OUTPUT 0
281 #define TIMER_0_LOAD_VALUE 99999
282 #define TIMER_0_MULT 0.001
283 #define TIMER_0_FREQ 100000000
284 #define ALT_MODULE_CLASS_timer_0 altera_avalon_timer
285 
286 /*
287  * timer_1 configuration
288  *
289  */
290 
291 #define TIMER_1_NAME "/dev/timer_1"
292 #define TIMER_1_TYPE "altera_avalon_timer"
293 #define TIMER_1_BASE 0x00681040
294 #define TIMER_1_SPAN 32
295 #define TIMER_1_IRQ 4
296 #define TIMER_1_ALWAYS_RUN 0
297 #define TIMER_1_FIXED_PERIOD 0
298 #define TIMER_1_SNAPSHOT 1
299 #define TIMER_1_PERIOD 1.0
300 #define TIMER_1_PERIOD_UNITS "ms"
301 #define TIMER_1_RESET_OUTPUT 0
302 #define TIMER_1_TIMEOUT_PULSE_OUTPUT 0
303 #define TIMER_1_LOAD_VALUE 99999
304 #define TIMER_1_MULT 0.001
305 #define TIMER_1_FREQ 100000000
306 #define ALT_MODULE_CLASS_timer_1 altera_avalon_timer
307 
308 /*
309  * lcd_16207_0 configuration
310  *
311  */
312 
313 #define LCD_16207_0_NAME "/dev/lcd_16207_0"
314 #define LCD_16207_0_TYPE "altera_avalon_lcd_16207"
315 #define LCD_16207_0_BASE 0x00681060
316 #define LCD_16207_0_SPAN 16
317 #define ALT_MODULE_CLASS_lcd_16207_0 altera_avalon_lcd_16207
318 
319 /*
320  * led_red configuration
321  *
322  */
323 
324 #define LED_RED_NAME "/dev/led_red"
325 #define LED_RED_TYPE "altera_avalon_pio"
326 #define LED_RED_BASE 0x00681070
327 #define LED_RED_SPAN 16
328 #define LED_RED_DO_TEST_BENCH_WIRING 0
329 #define LED_RED_DRIVEN_SIM_VALUE 0
330 #define LED_RED_HAS_TRI 0
331 #define LED_RED_HAS_OUT 1
332 #define LED_RED_HAS_IN 0
333 #define LED_RED_CAPTURE 0
334 #define LED_RED_DATA_WIDTH 18
335 #define LED_RED_EDGE_TYPE "NONE"
336 #define LED_RED_IRQ_TYPE "NONE"
337 #define LED_RED_BIT_CLEARING_EDGE_REGISTER 0
338 #define LED_RED_FREQ 100000000
339 #define ALT_MODULE_CLASS_led_red altera_avalon_pio
340 
341 /*
342  * led_green configuration
343  *
344  */
345 
346 #define LED_GREEN_NAME "/dev/led_green"
347 #define LED_GREEN_TYPE "altera_avalon_pio"
348 #define LED_GREEN_BASE 0x00681080
349 #define LED_GREEN_SPAN 16
350 #define LED_GREEN_DO_TEST_BENCH_WIRING 0
351 #define LED_GREEN_DRIVEN_SIM_VALUE 0
352 #define LED_GREEN_HAS_TRI 0
353 #define LED_GREEN_HAS_OUT 1
354 #define LED_GREEN_HAS_IN 0
355 #define LED_GREEN_CAPTURE 0
356 #define LED_GREEN_DATA_WIDTH 9
357 #define LED_GREEN_EDGE_TYPE "NONE"
358 #define LED_GREEN_IRQ_TYPE "NONE"
359 #define LED_GREEN_BIT_CLEARING_EDGE_REGISTER 0
360 #define LED_GREEN_FREQ 100000000
361 #define ALT_MODULE_CLASS_led_green altera_avalon_pio
362 
363 /*
364  * button_pio configuration
365  *
366  */
367 
368 #define BUTTON_PIO_NAME "/dev/button_pio"
369 #define BUTTON_PIO_TYPE "altera_avalon_pio"
370 #define BUTTON_PIO_BASE 0x00681090
371 #define BUTTON_PIO_SPAN 16
372 #define BUTTON_PIO_IRQ 5
373 #define BUTTON_PIO_DO_TEST_BENCH_WIRING 0
374 #define BUTTON_PIO_DRIVEN_SIM_VALUE 0
375 #define BUTTON_PIO_HAS_TRI 0
376 #define BUTTON_PIO_HAS_OUT 0
377 #define BUTTON_PIO_HAS_IN 1
378 #define BUTTON_PIO_CAPTURE 1
379 #define BUTTON_PIO_DATA_WIDTH 4
380 #define BUTTON_PIO_EDGE_TYPE "FALLING"
381 #define BUTTON_PIO_IRQ_TYPE "EDGE"
382 #define BUTTON_PIO_BIT_CLEARING_EDGE_REGISTER 0
383 #define BUTTON_PIO_FREQ 100000000
384 #define ALT_MODULE_CLASS_button_pio altera_avalon_pio
385 
386 /*
387  * switch_pio configuration
388  *
389  */
390 
391 #define SWITCH_PIO_NAME "/dev/switch_pio"
392 #define SWITCH_PIO_TYPE "altera_avalon_pio"
393 #define SWITCH_PIO_BASE 0x006810a0
394 #define SWITCH_PIO_SPAN 16
395 #define SWITCH_PIO_DO_TEST_BENCH_WIRING 0
396 #define SWITCH_PIO_DRIVEN_SIM_VALUE 0
397 #define SWITCH_PIO_HAS_TRI 0
398 #define SWITCH_PIO_HAS_OUT 0
399 #define SWITCH_PIO_HAS_IN 1
400 #define SWITCH_PIO_CAPTURE 0
401 #define SWITCH_PIO_DATA_WIDTH 18
402 #define SWITCH_PIO_EDGE_TYPE "NONE"
403 #define SWITCH_PIO_IRQ_TYPE "NONE"
404 #define SWITCH_PIO_BIT_CLEARING_EDGE_REGISTER 0
405 #define SWITCH_PIO_FREQ 100000000
406 #define ALT_MODULE_CLASS_switch_pio altera_avalon_pio
407 
408 /*
409  * SEG7_Display configuration
410  *
411  */
412 
413 #define SEG7_DISPLAY_NAME "/dev/SEG7_Display"
414 #define SEG7_DISPLAY_TYPE "seg7_lut_8"
415 #define SEG7_DISPLAY_BASE 0x00681100
416 #define SEG7_DISPLAY_SPAN 4
417 #define SEG7_DISPLAY_HDL_PARAMETERS ""
418 #define ALT_MODULE_CLASS_SEG7_Display seg7_lut_8
419 
420 /*
421  * sram_0 configuration
422  *
423  */
424 
425 #define SRAM_0_NAME "/dev/sram_0"
426 #define SRAM_0_TYPE "sram_16bit_512k"
427 #define SRAM_0_BASE 0x00600000
428 #define SRAM_0_SPAN 524288
429 #define SRAM_0_HDL_PARAMETERS ""
430 #define ALT_MODULE_CLASS_sram_0 sram_16bit_512k
431 
432 /*
433  * DM9000A configuration
434  *
435  */
436 
437 #define DM9000A_NAME "/dev/DM9000A"
438 #define DM9000A_TYPE "dm9000a"
439 #define DM9000A_BASE 0x006810f8
440 #define DM9000A_SPAN 8
441 #define DM9000A_IRQ 6
442 #define DM9000A_HDL_PARAMETERS ""
443 #define ALT_MODULE_CLASS_DM9000A dm9000a
444 
445 /*
446  * ISP1362/avalon_slave_0 configuration
447  *
448  */
449 
450 #define ISP1362_AVALON_SLAVE_0_NAME "/dev/ISP1362"
451 #define ISP1362_AVALON_SLAVE_0_TYPE "isp1362"
452 #define ISP1362_AVALON_SLAVE_0_BASE 0x006810b0
453 #define ISP1362_AVALON_SLAVE_0_SPAN 16
454 #define ISP1362_AVALON_SLAVE_0_IRQ 7
455 #define ISP1362_AVALON_SLAVE_0_HDL_PARAMETERS ""
456 #define ALT_MODULE_CLASS_ISP1362 isp1362
457 
458 /*
459  * ISP1362/avalon_slave_1 configuration
460  *
461  */
462 
463 #define ISP1362_AVALON_SLAVE_1_NAME "/dev/ISP1362"
464 #define ISP1362_AVALON_SLAVE_1_TYPE "isp1362"
465 #define ISP1362_AVALON_SLAVE_1_IRQ 8
466 #define ISP1362_AVALON_SLAVE_1_HDL_PARAMETERS ""
467 #define ALT_MODULE_CLASS_ISP1362 isp1362
468 
469 /*
470  * VGA_0 configuration
471  *
472  */
473 
474 #define VGA_0_NAME "/dev/VGA_0"
475 #define VGA_0_TYPE "binary_vga_controller"
476 #define VGA_0_BASE 0x00400000
477 #define VGA_0_SPAN 2097152
478 #define ALT_MODULE_CLASS_VGA_0 binary_vga_controller
479 
480 /*
481  * Audio_0 configuration
482  *
483  */
484 
485 #define AUDIO_0_NAME "/dev/Audio_0"
486 #define AUDIO_0_TYPE "audio_dac_fifo"
487 #define AUDIO_0_BASE 0x00681104
488 #define AUDIO_0_SPAN 4
489 #define ALT_MODULE_CLASS_Audio_0 audio_dac_fifo
490 
491 /*
492  * SD_DAT configuration
493  *
494  */
495 
496 #define SD_DAT_NAME "/dev/SD_DAT"
497 #define SD_DAT_TYPE "altera_avalon_pio"
498 #define SD_DAT_BASE 0x006810c0
499 #define SD_DAT_SPAN 16
500 #define SD_DAT_DO_TEST_BENCH_WIRING 0
501 #define SD_DAT_DRIVEN_SIM_VALUE 0
502 #define SD_DAT_HAS_TRI 1
503 #define SD_DAT_HAS_OUT 0
504 #define SD_DAT_HAS_IN 0
505 #define SD_DAT_CAPTURE 0
506 #define SD_DAT_DATA_WIDTH 1
507 #define SD_DAT_EDGE_TYPE "NONE"
508 #define SD_DAT_IRQ_TYPE "NONE"
509 #define SD_DAT_BIT_CLEARING_EDGE_REGISTER 0
510 #define SD_DAT_FREQ 100000000
511 #define ALT_MODULE_CLASS_SD_DAT altera_avalon_pio
512 
513 /*
514  * SD_CMD configuration
515  *
516  */
517 
518 #define SD_CMD_NAME "/dev/SD_CMD"
519 #define SD_CMD_TYPE "altera_avalon_pio"
520 #define SD_CMD_BASE 0x006810d0
521 #define SD_CMD_SPAN 16
522 #define SD_CMD_DO_TEST_BENCH_WIRING 0
523 #define SD_CMD_DRIVEN_SIM_VALUE 0
524 #define SD_CMD_HAS_TRI 1
525 #define SD_CMD_HAS_OUT 0
526 #define SD_CMD_HAS_IN 0
527 #define SD_CMD_CAPTURE 0
528 #define SD_CMD_DATA_WIDTH 1
529 #define SD_CMD_EDGE_TYPE "NONE"
530 #define SD_CMD_IRQ_TYPE "NONE"
531 #define SD_CMD_BIT_CLEARING_EDGE_REGISTER 0
532 #define SD_CMD_FREQ 100000000
533 #define ALT_MODULE_CLASS_SD_CMD altera_avalon_pio
534 
535 /*
536  * SD_CLK configuration
537  *
538  */
539 
540 #define SD_CLK_NAME "/dev/SD_CLK"
541 #define SD_CLK_TYPE "altera_avalon_pio"
542 #define SD_CLK_BASE 0x006810e0
543 #define SD_CLK_SPAN 16
544 #define SD_CLK_DO_TEST_BENCH_WIRING 0
545 #define SD_CLK_DRIVEN_SIM_VALUE 0
546 #define SD_CLK_HAS_TRI 0
547 #define SD_CLK_HAS_OUT 1
548 #define SD_CLK_HAS_IN 0
549 #define SD_CLK_CAPTURE 0
550 #define SD_CLK_DATA_WIDTH 1
551 #define SD_CLK_EDGE_TYPE "NONE"
552 #define SD_CLK_IRQ_TYPE "NONE"
553 #define SD_CLK_BIT_CLEARING_EDGE_REGISTER 0
554 #define SD_CLK_FREQ 100000000
555 #define ALT_MODULE_CLASS_SD_CLK altera_avalon_pio
556 
557 /*
558  * system library configuration
559  *
560  */
561 
562 #define ALT_MAX_FD 32
563 #define ALT_SYS_CLK TIMER_0
564 #define ALT_TIMESTAMP_CLK none
565 
566 /*
567  * Devices associated with code sections.
568  *
569  */
570 
571 #define ALT_TEXT_DEVICE       SDRAM_0
572 #define ALT_RODATA_DEVICE     SDRAM_0
573 #define ALT_RWDATA_DEVICE     SDRAM_0
574 #define ALT_EXCEPTIONS_DEVICE SDRAM_0
575 #define ALT_RESET_DEVICE      CFI_FLASH_0
576 
577 
578 #endif /* __SYSTEM_H_ */


413行

#define SEG7_DISPLAY_NAME "/dev/SEG7_Display"
#define SEG7_DISPLAY_TYPE "seg7_lut_8"
#define SEG7_DISPLAY_BASE 0x00681100
#define SEG7_DISPLAY_SPAN 4
#define SEG7_DISPLAY_HDL_PARAMETERS ""
#define ALT_MODULE_CLASS_SEG7_Display seg7_lut_8


我們發現和七段顯示器相關的巨集定義都在這,其中SEG7_DISPLAY_BASE定義的就是其base address,這也是為什麼在hello_world.c的第9行

#include <stdio.h>
#include 
"system.h"
#include 
"basic_io.h"


要include system.h和basic_io.h的原因。

完整程式碼下載
switch_seg7_sw.7z

Conclusion
本文的目的不只是在討論如何在Nios II用C語言去控制七段顯示器,重點是學習將來遇到新的controller時,要怎麼在軟體C語言中使用,如何到.h檔中找API?如何到system.h找定義base address的巨集?這才是更重要的。

See Also
(原創) 如何顯示8位數的七段顯示器? (IC Design) (Verilog) (DE2)
(原創) 如何自己用SOPC Builder建立一個能在DE2上跑μC/OS-II的Nios II系統? (IC Design) (DE2) (Quartus II) (Nios II) (SOPC Builder) (μC/OS-II)
(原創) 如何在Nios II使用16x2字元液晶顯示器? (IC Design) (DE2) (Nios II)
(原創) 如何以10進位顯示8位數的七段顯示器? (SOC) (Verilog) (DE2)
(原創) 如何在Nios II顯示8位數的七段顯示器? (SOC) (Nios II) (SOPC Builder) (DE2-70)

系统分类: CPLD/FPGA  |  用户分类: FPGA  |  标签: 无标签  |  来源: 转贴  | 

点击查看原文

发表评论 阅读全文(160) | 回复(0)

发表于 2009/12/7 10:42:43

0

关于投票

(转载) 如何在Nios II顯示8位數的七段顯示器? (IC Design) (DE2) (Nio

之前討論用硬體Verilog顯示8位數的七段顯示器,本文要討論在Nios II用軟體C語言控制8位數的七段顯示器。

Introduction
使用環境:Quartus II 7.2 SP1 + Nios II EDS 7.2 SP1 + DE2(Cyclone II EP2C35F627C6)

(原創) 如何顯示8位數的七段顯示器? (IC Design) (Verilog) (DE2)曾經討論過用硬體Verilog顯示8位數的七段顯示器,今天剛好有需要想在Nios II從軟體C語言去控制七段顯示器,本來想自己寫一個custom component,後來發現友晶的NIOS II Reference Design已經寫好了,只要會『用』就好了。

Nios II的Reference Design放在DE2 CD中的\DE2_demonstrations\SOPC_Builder\Reference_Design\下,(或從http://www.terasic.com/downloads/cd-rom/de2/ 下載),若你想自己從頭到尾自己由SOPC Builder建立,請參閱(原創) 如何自己用SOPC Builder建立一個能在DE2上跑μC/OS-II的Nios II系統? (IC Design) (DE2) (Quartus II) (Nios II) (SOPC Builder) (μC/OS-II)

C語言  / hello_world.c

 1 /* 
 2 (C) OOMusou 2008 http://oomusou.cnblogs.com
 3 
 4 Filename    : hello_world.c
 5 Compiler    : Nios II gcc
 6 Description : Demo how to display 7 seg.
 7 Release     : 04/27/2008 1.0
 8 */
 9 #include <stdio.h>
10 #include "system.h"
11 #include "basic_io.h"
12 
13 int main() {
14   int i;
15   for(i = 0; i != 100; i++)  {
16     Sleep(1);
17     seg7_show(SEG7_DISPLAY_BASE, i);
18   }
19 }
20 


你一定會問我,怎麼知道seg7_show()這個API可以在Nios II使用?我是在SEG7_LUT_8這個目錄下的inc\basic_io.h知道的,因為一個custom component一定會有一個include檔定義軟體能用的API。

C語言 / basic_io.h

 1 #ifndef   __basic_io_H__
 2 #define   __basic_io_H__
 3 
 4 #include <io.h>
 5 #include <stdio.h>
 6 #include <unistd.h>
 7 #include <stdlib.h>
 8 #include "system.h"
 9 #include "sys/alt_irq.h"
10 
11 //  for GPIO
12 #define inport(base)                                  IORD(base, 0) 
13 #define outport(base, data)                           IOWR(base, 0, data)
14 #define get_pio_dir(base)                             IORD(base, 1) 
15 #define set_pio_dir(base, data)                       IOWR(base, 1, data)
16 #define get_pio_irq_mask(base)                        IORD(base, 2) 
17 #define set_pio_irq_mask(base, data)                  IOWR(base, 2, data)
18 #define get_pio_edge_cap(base)                        IORD(base, 3) 
19 #define set_pio_edge_cap(base, data)                  IOWR(base, 3, data)
20 
21 //  for SEG7 Display
22 #define seg7_show(base,data)                          IOWR(base, 0, data)
23 
24 //  for Time Delay
25 #define msleep(msec)                                  usleep(1000*msec);
26 #define Sleep(sec)                                    msleep(1000*sec);
27 
28 #endif


21行

//  for SEG7 Display
#define seg7_show(base,data)                          IOWR(base, 0, data)


我們發現了seg7_show()這個巨集,所以知道用這個巨集可以控制七段顯示器。

問題又來了,他要我們傳入七段顯示器的base address,我們要怎麼知道呢?

在SOPC Builder會分配每個component的base address,Nios II EDS在產生system library時,會將所有的address定義在\software\hello_world_0_syslib\Debug\system_description\system.h下。

C語言 / system.h

  1 /* system.h
  2  *
  3  * Machine generated for a CPU named "cpu_0" as defined in:
  4  * c:\0Clare\DE2\switch_seg7_ip\software\hello_world_0_syslib\..\..\system_0.ptf
  5  *
  6  * Generated: 2008-04-27 00:14:19.203
  7  *
  8  */
  9 
 10 #ifndef __SYSTEM_H_
 11 #define __SYSTEM_H_
 12 
 13 /*
 14 
 15 DO NOT MODIFY THIS FILE
 16 
 17    Changing this file will have subtle consequences
 18    which will almost certainly lead to a nonfunctioning
 19    system. If you do modify this file, be aware that your
 20    changes will be overwritten and lost when this file
 21    is generated again.
 22 
 23 DO NOT MODIFY THIS FILE
 24 
 25 */
 26 
 27 /******************************************************************************
 28 *                                                                             *
 29 * License Agreement                                                           *
 30 *                                                                             *
 31 * Copyright (c) 2003 Altera Corporation, San Jose, California, USA.           *
 32 * All rights reserved.                                                        *
 33 *                                                                             *
 34 * Permission is hereby granted, free of charge, to any person obtaining a     *
 35 * copy of this software and associated documentation files (the "Software"),  *
 36 * to deal in the Software without restriction, including without limitation   *
 37 * the rights to use, copy, modify, merge, publish, distribute, sublicense,    *
 38 * and/or sell copies of the Software, and to permit persons to whom the       *
 39 * Software is furnished to do so, subject to the following conditions:        *
 40 *                                                                             *
 41 * The above copyright notice and this permission notice shall be included in  *
 42 * all copies or substantial portions of the Software.                         *
 43 *                                                                             *
 44 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR  *
 45 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,    *
 46 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE *
 47 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER      *
 48 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING     *
 49 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER         *
 50 * DEALINGS IN THE SOFTWARE.                                                   *
 51 *                                                                             *
 52 * This agreement shall be governed in all respects by the laws of the State   *
 53 * of California and by the laws of the United States of America.              *
 54 *                                                                             *
 55 ******************************************************************************/
 56 
 57 /*
 58  * system configuration
 59  *
 60  */
 61 
 62 #define ALT_SYSTEM_NAME "system_0"
 63 #define ALT_CPU_NAME "cpu_0"
 64 #define ALT_CPU_ARCHITECTURE "altera_nios2"
 65 #define ALT_DEVICE_FAMILY "CYCLONEII"
 66 #define ALT_STDIN "/dev/jtag_uart_0"
 67 #define ALT_STDIN_TYPE "altera_avalon_jtag_uart"
 68 #define ALT_STDIN_BASE 0x006810f0
 69 #define ALT_STDIN_DEV jtag_uart_0
 70 #define ALT_STDIN_PRESENT
 71 #define ALT_STDOUT "/dev/jtag_uart_0"
 72 #define ALT_STDOUT_TYPE "altera_avalon_jtag_uart"
 73 #define ALT_STDOUT_BASE 0x006810f0
 74 #define ALT_STDOUT_DEV jtag_uart_0
 75 #define ALT_STDOUT_PRESENT
 76 #define ALT_STDERR "/dev/jtag_uart_0"
 77 #define ALT_STDERR_TYPE "altera_avalon_jtag_uart"
 78 #define ALT_STDERR_BASE 0x006810f0
 79 #define ALT_STDERR_DEV jtag_uart_0
 80 #define ALT_STDERR_PRESENT
 81 #define ALT_CPU_FREQ 100000000
 82 #define ALT_IRQ_BASE NULL
 83 
 84 /*
 85  * processor configuration
 86  *
 87  */
 88 
 89 #define NIOS2_CPU_IMPLEMENTATION "fast"
 90 #define NIOS2_BIG_ENDIAN 0
 91 
 92 #define NIOS2_ICACHE_SIZE 4096
 93 #define NIOS2_DCACHE_SIZE 2048
 94 #define NIOS2_ICACHE_LINE_SIZE 32
 95 #define NIOS2_ICACHE_LINE_SIZE_LOG2 5
 96 #define NIOS2_DCACHE_LINE_SIZE 4
 97 #define NIOS2_DCACHE_LINE_SIZE_LOG2 2
 98 #define NIOS2_FLUSHDA_SUPPORTED
 99 
100 #define NIOS2_EXCEPTION_ADDR 0x00800020
101 #define NIOS2_RESET_ADDR 0x00000000
102 #define NIOS2_BREAK_ADDR 0x00680020
103 
104 #define NIOS2_HAS_DEBUG_STUB
105 
106 #define NIOS2_CPU_ID_SIZE 1
107 #define NIOS2_CPU_ID_VALUE 0
108 
109 /*
110  * A define for each class of peripheral
111  *
112  */
113 
114 #define __ALTERA_AVALON_TRI_STATE_BRIDGE
115 #define __ALTERA_AVALON_CFI_FLASH
116 #define __ALTERA_AVALON_NEW_SDRAM_CONTROLLER
117 #define __ALTERA_AVALON_EPCS_FLASH_CONTROLLER
118 #define __ALTERA_AVALON_JTAG_UART
119 #define __ALTERA_AVALON_UART
120 #define __ALTERA_AVALON_TIMER
121 #define __ALTERA_AVALON_LCD_16207
122 #define __ALTERA_AVALON_PIO
123 #define __SEG7_LUT_8
124 #define __SRAM_16BIT_512K
125 #define __DM9000A
126 #define __ISP1362
127 #define __BINARY_VGA_CONTROLLER
128 #define __AUDIO_DAC_FIFO
129 
130 /*
131  * tri_state_bridge_0 configuration
132  *
133  */
134 
135 #define TRI_STATE_BRIDGE_0_NAME "/dev/tri_state_bridge_0"
136 #define TRI_STATE_BRIDGE_0_TYPE "altera_avalon_tri_state_bridge"
137 #define ALT_MODULE_CLASS_tri_state_bridge_0 altera_avalon_tri_state_bridge
138 
139 /*
140  * cfi_flash_0 configuration
141  *
142  */
143 
144 #define CFI_FLASH_0_NAME "/dev/cfi_flash_0"
145 #define CFI_FLASH_0_TYPE "altera_avalon_cfi_flash"
146 #define CFI_FLASH_0_BASE 0x00000000
147 #define CFI_FLASH_0_SPAN 4194304
148 #define CFI_FLASH_0_SETUP_VALUE 40
149 #define CFI_FLASH_0_WAIT_VALUE 160
150 #define CFI_FLASH_0_HOLD_VALUE 40
151 #define CFI_FLASH_0_TIMING_UNITS "ns"
152 #define CFI_FLASH_0_UNIT_MULTIPLIER 1
153 #define CFI_FLASH_0_SIZE 4194304
154 #define ALT_MODULE_CLASS_cfi_flash_0 altera_avalon_cfi_flash
155 
156 /*
157  * sdram_0 configuration
158  *
159  */
160 
161 #define SDRAM_0_NAME "/dev/sdram_0"
162 #define SDRAM_0_TYPE "altera_avalon_new_sdram_controller"
163 #define SDRAM_0_BASE 0x00800000
164 #define SDRAM_0_SPAN 8388608
165 #define SDRAM_0_REGISTER_DATA_IN 1
166 #define SDRAM_0_SIM_MODEL_BASE 1
167 #define SDRAM_0_SDRAM_DATA_WIDTH 16
168 #define SDRAM_0_SDRAM_ADDR_WIDTH 12
169 #define SDRAM_0_SDRAM_ROW_WIDTH 12
170 #define SDRAM_0_SDRAM_COL_WIDTH 8
171 #define SDRAM_0_SDRAM_NUM_CHIPSELECTS 1
172 #define SDRAM_0_SDRAM_NUM_BANKS 4
173 #define SDRAM_0_REFRESH_PERIOD 15.625
174 #define SDRAM_0_POWERUP_DELAY 100.0
175 #define SDRAM_0_CAS_LATENCY 3
176 #define SDRAM_0_T_RFC 70.0
177 #define SDRAM_0_T_RP 20.0
178 #define SDRAM_0_T_MRD 3
179 #define SDRAM_0_T_RCD 20.0
180 #define SDRAM_0_T_AC 5.5
181 #define SDRAM_0_T_WR 14.0
182 #define SDRAM_0_INIT_REFRESH_COMMANDS 2
183 #define SDRAM_0_INIT_NOP_DELAY 0.0
184 #define SDRAM_0_SHARED_DATA 0
185 #define SDRAM_0_SDRAM_BANK_WIDTH 2
186 #define SDRAM_0_TRISTATE_BRIDGE_SLAVE ""
187 #define SDRAM_0_STARVATION_INDICATOR 0
188 #define SDRAM_0_IS_INITIALIZED 1
189 #define ALT_MODULE_CLASS_sdram_0 altera_avalon_new_sdram_controller
190 
191 /*
192  * epcs_controller configuration
193  *
194  */
195 
196 #define EPCS_CONTROLLER_NAME "/dev/epcs_controller"
197 #define EPCS_CONTROLLER_TYPE "altera_avalon_epcs_flash_controller"
198 #define EPCS_CONTROLLER_BASE 0x00680800
199 #define EPCS_CONTROLLER_SPAN 2048
200 #define EPCS_CONTROLLER_IRQ 0
201 #define EPCS_CONTROLLER_DATABITS 8
202 #define EPCS_CONTROLLER_TARGETCLOCK 20
203 #define EPCS_CONTROLLER_CLOCKUNITS "MHz"
204 #define EPCS_CONTROLLER_CLOCKMULT 1000000
205 #define EPCS_CONTROLLER_NUMSLAVES 1
206 #define EPCS_CONTROLLER_ISMASTER 1
207 #define EPCS_CONTROLLER_CLOCKPOLARITY 0
208 #define EPCS_CONTROLLER_CLOCKPHASE 0
209 #define EPCS_CONTROLLER_LSBFIRST 0
210 #define EPCS_CONTROLLER_EXTRADELAY 0
211 #define EPCS_CONTROLLER_TARGETSSDELAY 100
212 #define EPCS_CONTROLLER_DELAYUNITS "us"
213 #define EPCS_CONTROLLER_DELAYMULT "1e-006"
214 #define EPCS_CONTROLLER_PREFIX "epcs_"
215 #define EPCS_CONTROLLER_REGISTER_OFFSET 0x200
216 #define EPCS_CONTROLLER_USE_ASMI_ATOM 1
217 #define EPCS_CONTROLLER_CLOCKUNIT "kHz"
218 #define EPCS_CONTROLLER_DELAYUNIT "us"
219 #define ALT_MODULE_CLASS_epcs_controller altera_avalon_epcs_flash_controller
220 
221 /*
222  * jtag_uart_0 configuration
223  *
224  */
225 
226 #define JTAG_UART_0_NAME "/dev/jtag_uart_0"
227 #define JTAG_UART_0_TYPE "altera_avalon_jtag_uart"
228 #define JTAG_UART_0_BASE 0x006810f0
229 #define JTAG_UART_0_SPAN 8
230 #define JTAG_UART_0_IRQ 1
231 #define JTAG_UART_0_WRITE_DEPTH 64
232 #define JTAG_UART_0_READ_DEPTH 64
233 #define JTAG_UART_0_WRITE_THRESHOLD 8
234 #define JTAG_UART_0_READ_THRESHOLD 8
235 #define JTAG_UART_0_READ_CHAR_STREAM ""
236 #define JTAG_UART_0_SHOWASCII 1
237 #define JTAG_UART_0_READ_LE 0
238 #define JTAG_UART_0_WRITE_LE 0
239 #define JTAG_UART_0_ALTERA_SHOW_UNRELEASED_JTAG_UART_FEATURES 0
240 #define ALT_MODULE_CLASS_jtag_uart_0 altera_avalon_jtag_uart
241 
242 /*
243  * uart_0 configuration
244  *
245  */
246 
247 #define UART_0_NAME "/dev/uart_0"
248 #define UART_0_TYPE "altera_avalon_uart"
249 #define UART_0_BASE 0x00681000
250 #define UART_0_SPAN 32
251 #define UART_0_IRQ 2
252 #define UART_0_BAUD 115200
253 #define UART_0_DATA_BITS 8
254 #define UART_0_FIXED_BAUD 1
255 #define UART_0_PARITY 'N'
256 #define UART_0_STOP_BITS 1
257 #define UART_0_USE_CTS_RTS 0
258 #define UART_0_USE_EOP_REGISTER 0
259 #define UART_0_SIM_TRUE_BAUD 0
260 #define UART_0_SIM_CHAR_STREAM ""
261 #define UART_0_FREQ 100000000
262 #define ALT_MODULE_CLASS_uart_0 altera_avalon_uart
263 
264 /*
265  * timer_0 configuration
266  *
267  */
268 
269 #define TIMER_0_NAME "/dev/timer_0"
270 #define TIMER_0_TYPE "altera_avalon_timer"
271 #define TIMER_0_BASE 0x00681020
272 #define TIMER_0_SPAN 32
273 #define TIMER_0_IRQ 3
274 #define TIMER_0_ALWAYS_RUN 0
275 #define TIMER_0_FIXED_PERIOD 0
276 #define TIMER_0_SNAPSHOT 1
277 #define TIMER_0_PERIOD 1.0
278 #define TIMER_0_PERIOD_UNITS "ms"
279 #define TIMER_0_RESET_OUTPUT 0
280 #define TIMER_0_TIMEOUT_PULSE_OUTPUT 0
281 #define TIMER_0_LOAD_VALUE 99999
282 #define TIMER_0_MULT 0.001
283 #define TIMER_0_FREQ 100000000
284 #define ALT_MODULE_CLASS_timer_0 altera_avalon_timer
285 
286 /*
287  * timer_1 configuration
288  *
289  */
290 
291 #define TIMER_1_NAME "/dev/timer_1"
292 #define TIMER_1_TYPE "altera_avalon_timer"
293 #define TIMER_1_BASE 0x00681040
294 #define TIMER_1_SPAN 32
295 #define TIMER_1_IRQ 4
296 #define TIMER_1_ALWAYS_RUN 0
297 #define TIMER_1_FIXED_PERIOD 0
298 #define TIMER_1_SNAPSHOT 1
299 #define TIMER_1_PERIOD 1.0
300 #define TIMER_1_PERIOD_UNITS "ms"
301 #define TIMER_1_RESET_OUTPUT 0
302 #define TIMER_1_TIMEOUT_PULSE_OUTPUT 0
303 #define TIMER_1_LOAD_VALUE 99999
304 #define TIMER_1_MULT 0.001
305 #define TIMER_1_FREQ 100000000
306 #define ALT_MODULE_CLASS_timer_1 altera_avalon_timer
307 
308 /*
309  * lcd_16207_0 configuration
310  *
311  */
312 
313 #define LCD_16207_0_NAME "/dev/lcd_16207_0"
314 #define LCD_16207_0_TYPE "altera_avalon_lcd_16207"
315 #define LCD_16207_0_BASE 0x00681060
316 #define LCD_16207_0_SPAN 16
317 #define ALT_MODULE_CLASS_lcd_16207_0 altera_avalon_lcd_16207
318 
319 /*
320  * led_red configuration
321  *
322  */
323 
324 #define LED_RED_NAME "/dev/led_red"
325 #define LED_RED_TYPE "altera_avalon_pio"
326 #define LED_RED_BASE 0x00681070
327 #define LED_RED_SPAN 16
328 #define LED_RED_DO_TEST_BENCH_WIRING 0
329 #define LED_RED_DRIVEN_SIM_VALUE 0
330 #define LED_RED_HAS_TRI 0
331 #define LED_RED_HAS_OUT 1
332 #define LED_RED_HAS_IN 0
333 #define LED_RED_CAPTURE 0
334 #define LED_RED_DATA_WIDTH 18
335 #define LED_RED_EDGE_TYPE "NONE"
336 #define LED_RED_IRQ_TYPE "NONE"
337 #define LED_RED_BIT_CLEARING_EDGE_REGISTER 0
338 #define LED_RED_FREQ 100000000
339 #define ALT_MODULE_CLASS_led_red altera_avalon_pio
340 
341 /*
342  * led_green configuration
343  *
344  */
345 
346 #define LED_GREEN_NAME "/dev/led_green"
347 #define LED_GREEN_TYPE "altera_avalon_pio"
348 #define LED_GREEN_BASE 0x00681080
349 #define LED_GREEN_SPAN 16
350 #define LED_GREEN_DO_TEST_BENCH_WIRING 0
351 #define LED_GREEN_DRIVEN_SIM_VALUE 0
352 #define LED_GREEN_HAS_TRI 0
353 #define LED_GREEN_HAS_OUT 1
354 #define LED_GREEN_HAS_IN 0
355 #define LED_GREEN_CAPTURE 0
356 #define LED_GREEN_DATA_WIDTH 9
357 #define LED_GREEN_EDGE_TYPE "NONE"
358 #define LED_GREEN_IRQ_TYPE "NONE"
359 #define LED_GREEN_BIT_CLEARING_EDGE_REGISTER 0
360 #define LED_GREEN_FREQ 100000000
361 #define ALT_MODULE_CLASS_led_green altera_avalon_pio
362 
363 /*
364  * button_pio configuration
365  *
366  */
367 
368 #define BUTTON_PIO_NAME "/dev/button_pio"
369 #define BUTTON_PIO_TYPE "altera_avalon_pio"
370 #define BUTTON_PIO_BASE 0x00681090
371 #define BUTTON_PIO_SPAN 16
372 #define BUTTON_PIO_IRQ 5
373 #define BUTTON_PIO_DO_TEST_BENCH_WIRING 0
374 #define BUTTON_PIO_DRIVEN_SIM_VALUE 0
375 #define BUTTON_PIO_HAS_TRI 0
376 #define BUTTON_PIO_HAS_OUT 0
377 #define BUTTON_PIO_HAS_IN 1
378 #define BUTTON_PIO_CAPTURE 1
379 #define BUTTON_PIO_DATA_WIDTH 4
380 #define BUTTON_PIO_EDGE_TYPE "FALLING"
381 #define BUTTON_PIO_IRQ_TYPE "EDGE"
382 #define BUTTON_PIO_BIT_CLEARING_EDGE_REGISTER 0
383 #define BUTTON_PIO_FREQ 100000000
384 #define ALT_MODULE_CLASS_button_pio altera_avalon_pio
385 
386 /*
387  * switch_pio configuration
388  *
389  */
390 
391 #define SWITCH_PIO_NAME "/dev/switch_pio"
392 #define SWITCH_PIO_TYPE "altera_avalon_pio"
393 #define SWITCH_PIO_BASE 0x006810a0
394 #define SWITCH_PIO_SPAN 16
395 #define SWITCH_PIO_DO_TEST_BENCH_WIRING 0
396 #define SWITCH_PIO_DRIVEN_SIM_VALUE 0
397 #define SWITCH_PIO_HAS_TRI 0
398 #define SWITCH_PIO_HAS_OUT 0
399 #define SWITCH_PIO_HAS_IN 1
400 #define SWITCH_PIO_CAPTURE 0
401 #define SWITCH_PIO_DATA_WIDTH 18
402 #define SWITCH_PIO_EDGE_TYPE "NONE"
403 #define SWITCH_PIO_IRQ_TYPE "NONE"
404 #define SWITCH_PIO_BIT_CLEARING_EDGE_REGISTER 0
405 #define SWITCH_PIO_FREQ 100000000
406 #define ALT_MODULE_CLASS_switch_pio altera_avalon_pio
407 
408 /*
409  * SEG7_Display configuration
410  *
411  */
412 
413 #define SEG7_DISPLAY_NAME "/dev/SEG7_Display"
414 #define SEG7_DISPLAY_TYPE "seg7_lut_8"
415 #define SEG7_DISPLAY_BASE 0x00681100
416 #define SEG7_DISPLAY_SPAN 4
417 #define SEG7_DISPLAY_HDL_PARAMETERS ""
418 #define ALT_MODULE_CLASS_SEG7_Display seg7_lut_8
419 
420 /*
421  * sram_0 configuration
422  *
423  */
424 
425 #define SRAM_0_NAME "/dev/sram_0"
426 #define SRAM_0_TYPE "sram_16bit_512k"
427 #define SRAM_0_BASE 0x00600000
428 #define SRAM_0_SPAN 524288
429 #define SRAM_0_HDL_PARAMETERS ""
430 #define ALT_MODULE_CLASS_sram_0 sram_16bit_512k
431 
432 /*
433  * DM9000A configuration
434  *
435  */
436 
437 #define DM9000A_NAME "/dev/DM9000A"
438 #define DM9000A_TYPE "dm9000a"
439 #define DM9000A_BASE 0x006810f8
440 #define DM9000A_SPAN 8
441 #define DM9000A_IRQ 6
442 #define DM9000A_HDL_PARAMETERS ""
443 #define ALT_MODULE_CLASS_DM9000A dm9000a
444 
445 /*
446  * ISP1362/avalon_slave_0 configuration
447  *
448  */
449 
450 #define ISP1362_AVALON_SLAVE_0_NAME "/dev/ISP1362"
451 #define ISP1362_AVALON_SLAVE_0_TYPE "isp1362"
452 #define ISP1362_AVALON_SLAVE_0_BASE 0x006810b0
453 #define ISP1362_AVALON_SLAVE_0_SPAN 16
454 #define ISP1362_AVALON_SLAVE_0_IRQ 7
455 #define ISP1362_AVALON_SLAVE_0_HDL_PARAMETERS ""
456 #define ALT_MODULE_CLASS_ISP1362 isp1362
457 
458 /*
459  * ISP1362/avalon_slave_1 configuration
460  *
461  */
462 
463 #define ISP1362_AVALON_SLAVE_1_NAME "/dev/ISP1362"
464 #define ISP1362_AVALON_SLAVE_1_TYPE "isp1362"
465 #define ISP1362_AVALON_SLAVE_1_IRQ 8
466 #define ISP1362_AVALON_SLAVE_1_HDL_PARAMETERS ""
467 #define ALT_MODULE_CLASS_ISP1362 isp1362
468 
469 /*
470  * VGA_0 configuration
471  *
472  */
473 
474 #define VGA_0_NAME "/dev/VGA_0"
475 #define VGA_0_TYPE "binary_vga_controller"
476 #define VGA_0_BASE 0x00400000
477 #define VGA_0_SPAN 2097152
478 #define ALT_MODULE_CLASS_VGA_0 binary_vga_controller
479 
480 /*
481  * Audio_0 configuration
482  *
483  */
484 
485 #define AUDIO_0_NAME "/dev/Audio_0"
486 #define AUDIO_0_TYPE "audio_dac_fifo"
487 #define AUDIO_0_BASE 0x00681104
488 #define AUDIO_0_SPAN 4
489 #define ALT_MODULE_CLASS_Audio_0 audio_dac_fifo
490 
491 /*
492  * SD_DAT configuration
493  *
494  */
495 
496 #define SD_DAT_NAME "/dev/SD_DAT"
497 #define SD_DAT_TYPE "altera_avalon_pio"
498 #define SD_DAT_BASE 0x006810c0
499 #define SD_DAT_SPAN 16
500 #define SD_DAT_DO_TEST_BENCH_WIRING 0
501 #define SD_DAT_DRIVEN_SIM_VALUE 0
502 #define SD_DAT_HAS_TRI 1
503 #define SD_DAT_HAS_OUT 0
504 #define SD_DAT_HAS_IN 0
505 #define SD_DAT_CAPTURE 0
506 #define SD_DAT_DATA_WIDTH 1
507 #define SD_DAT_EDGE_TYPE "NONE"
508 #define SD_DAT_IRQ_TYPE "NONE"
509 #define SD_DAT_BIT_CLEARING_EDGE_REGISTER 0
510 #define SD_DAT_FREQ 100000000
511 #define ALT_MODULE_CLASS_SD_DAT altera_avalon_pio
512 
513 /*
514  * SD_CMD configuration
515  *
516  */
517 
518 #define SD_CMD_NAME "/dev/SD_CMD"
519 #define SD_CMD_TYPE "altera_avalon_pio"
520 #define SD_CMD_BASE 0x006810d0
521 #define SD_CMD_SPAN 16
522 #define SD_CMD_DO_TEST_BENCH_WIRING 0
523 #define SD_CMD_DRIVEN_SIM_VALUE 0
524 #define SD_CMD_HAS_TRI 1
525 #define SD_CMD_HAS_OUT 0
526 #define SD_CMD_HAS_IN 0
527 #define SD_CMD_CAPTURE 0
528 #define SD_CMD_DATA_WIDTH 1
529 #define SD_CMD_EDGE_TYPE "NONE"
530 #define SD_CMD_IRQ_TYPE "NONE"
531 #define SD_CMD_BIT_CLEARING_EDGE_REGISTER 0
532 #define SD_CMD_FREQ 100000000
533 #define ALT_MODULE_CLASS_SD_CMD altera_avalon_pio
534 
535 /*
536  * SD_CLK configuration
537  *
538  */
539 
540 #define SD_CLK_NAME "/dev/SD_CLK"
541 #define SD_CLK_TYPE "altera_avalon_pio"
542 #define SD_CLK_BASE 0x006810e0
543 #define SD_CLK_SPAN 16
544 #define SD_CLK_DO_TEST_BENCH_WIRING 0
545 #define SD_CLK_DRIVEN_SIM_VALUE 0
546 #define SD_CLK_HAS_TRI 0
547 #define SD_CLK_HAS_OUT 1
548 #define SD_CLK_HAS_IN 0
549 #define SD_CLK_CAPTURE 0
550 #define SD_CLK_DATA_WIDTH 1
551 #define SD_CLK_EDGE_TYPE "NONE"
552 #define SD_CLK_IRQ_TYPE "NONE"
553 #define SD_CLK_BIT_CLEARING_EDGE_REGISTER 0
554 #define SD_CLK_FREQ 100000000
555 #define ALT_MODULE_CLASS_SD_CLK altera_avalon_pio
556 
557 /*
558  * system library configuration
559  *
560  */
561 
562 #define ALT_MAX_FD 32
563 #define ALT_SYS_CLK TIMER_0
564 #define ALT_TIMESTAMP_CLK none
565 
566 /*
567  * Devices associated with code sections.
568  *
569  */
570 
571 #define ALT_TEXT_DEVICE       SDRAM_0
572 #define ALT_RODATA_DEVICE     SDRAM_0
573 #define ALT_RWDATA_DEVICE     SDRAM_0
574 #define ALT_EXCEPTIONS_DEVICE SDRAM_0
575 #define ALT_RESET_DEVICE      CFI_FLASH_0
576 
577 
578 #endif /* __SYSTEM_H_ */


413行

#define SEG7_DISPLAY_NAME "/dev/SEG7_Display"
#define SEG7_DISPLAY_TYPE "seg7_lut_8"
#define SEG7_DISPLAY_BASE 0x00681100
#define SEG7_DISPLAY_SPAN 4
#define SEG7_DISPLAY_HDL_PARAMETERS ""
#define ALT_MODULE_CLASS_SEG7_Display seg7_lut_8


我們發現和七段顯示器相關的巨集定義都在這,其中SEG7_DISPLAY_BASE定義的就是其base address,這也是為什麼在hello_world.c的第9行

#include <stdio.h>
#include 
"system.h"
#include 
"basic_io.h"


要include system.h和basic_io.h的原因。

完整程式碼下載
switch_seg7_sw.7z

Conclusion
本文的目的不只是在討論如何在Nios II用C語言去控制七段顯示器,重點是學習將來遇到新的controller時,要怎麼在軟體C語言中使用,如何到.h檔中找API?如何到system.h找定義base address的巨集?這才是更重要的。

See Also
(原創) 如何顯示8位數的七段顯示器? (IC Design) (Verilog) (DE2)
(原創) 如何自己用SOPC Builder建立一個能在DE2上跑μC/OS-II的Nios II系統? (IC Design) (DE2) (Quartus II) (Nios II) (SOPC Builder) (μC/OS-II)
(原創) 如何在Nios II使用16x2字元液晶顯示器? (IC Design) (DE2) (Nios II)
(原創) 如何以10進位顯示8位數的七段顯示器? (SOC) (Verilog) (DE2)
(原創) 如何在Nios II顯示8位數的七段顯示器? (SOC) (Nios II) (SOPC Builder) (DE2-70)

系统分类: CPLD/FPGA  |  用户分类: FPGA  |  标签: 无标签  |  来源: 转贴  | 

点击查看原文

发表评论 阅读全文(99) | 回复(0)

发表于 2009/12/7 1:08:38

0

关于投票

(原創) 如何在Nios II顯示8位數的七段顯示器? (SOC) (Nios II) (SOPC

本文討論如何在Nios II控制8位數的七段顯示器。

Introduction
使用環境:Quartus II 8.0 + Nios II EDS 8.0 + DE2-70 (Cyclone II EP2C70F896C6N)

(原創) 如何在Nios II顯示8位數的七段顯示器? (IC Design) (DE2) (Nios II)討論的是DE2平台,到了DE2-70平台,控制七段顯示器的方式有些改變:

1.七段顯示器多了8個小數點可控制。
2.友晶科技提供了新的七段顯示器ip,其HAL也不太一樣。

本文使用(原創) 哪裡有DE2-70的Nios II reference design可以參考? (SOC) (DE2-70) (Nios II) (SOPC Builder)所提供的範例為基礎討論。

SOPC Builder部分
使用友晶科技所提供SEG7_IF ip

点击看大图

Top Module部分
請參考(原創) 哪裡有DE2-70的Nios II reference design可以參考? (SOC) (DE2-70) (Nios II) (SOPC Builder)

使用HAL控制七段顯示器

將\DE2_70_NIOS_10_seg7\ip\TERASIC_SEG7\software\的SEG7.c與SEG7.h 複製到\DE2_70_NIOS_10_seg7\software\hello_world_0\,必須將SEG7.h與SEG7.c做些修改。

SEG7.h / C 

1 #ifndef SEG7_H_
2 #define SEG7_H_
3 
4 #include "alt_types.h"
5 
6 void SEG7_Clear(void);
7 void SEG7_Full(void);
8 void SEG7_Hex(alt_u32 Data, alt_u8 point_mask);
9 void SEG7_Decimal(alt_u32 Data, alt_u8 point_mask);
10 void SEG7_Number(void);
11 
12 #endif /*SEG7_H_*/


4行

#include "alt_types.h"


增加inlucde alt_types.h,因為alt_u32定義在alt_types.h

6行

void SEG7_Clear(void);
void SEG7_Full(void);
void SEG7_Hex(alt_u32 Data, alt_u8 point_mask);
void SEG7_Decimal(alt_u32 Data, alt_u8 point_mask);
void SEG7_Number(void);


提供5個HAL讓我們可以在Nios II用C去控制七段顯示器。

SEG7_Clear():將8個七段顯示器全部清空不顯示(不是0,是完全不顯示)。
SEG7_Full():將8個七段顯示器全部顯示8。
SEG7_Hex():將8個七段顯示器以16進位顯示,第2個參數可控制小數點,如0x10表示顯示第5個小數點。
SEG7_Decimal():將8個七段顯示器以10進位顯示,第2個參數可控制小數點,如0x10表示顯示第5個小數點。
SEG7_Numer(): 將8個七段顯示器從左至右顯示76543210。

SEG7.c / C

1 #include "system.h"
2 #include "alt_types.h"
3 #include "io.h"
4 #include "SEG7.h"
5 
6 #define SEG7_SET(index, seg_mask) IOWR(SEG7_BASE,index,seg_mask)
7 #define SEG7_NUM 8
8 
9 static unsigned char szMap[] = {
10   63, 6, 91, 79, 102, 109, 125, 7,
11   127, 111, 119, 124, 57, 94, 121, 113
12 };  // 0,1,2,.9, a, b, c, d, e, f
13    
14 void SEG7_Clear(void) {
15   int i;
16  
17   for(i=0; i<SEG7_NUM; i++)
18     SEG7_SET(i, 0x00);
19 }
20 
21 void SEG7_Full(void) {
22   int i;
23  
24   for(i=0; i<SEG7_NUM; i++)
25     SEG7_SET(i, 0xFF);
26 }
27 
28 void SEG7_Number(void) {
29   int i;
30 
31   for(i=0;i<SEG7_NUM;i++)
32     SEG7_SET(i, szMap[i]);
33 }
34 
35 void SEG7_Hex(alt_u32 Data, alt_u8 point_mask) {
36   alt_u8 mask = 0x01;
37   alt_u8 seg_mask;
38   int i;
39    
40   seg_mask = 0;
41   for(i = 0; i < SEG7_NUM; i++) {
42     seg_mask = szMap[Data & 0x0F];
43     Data >>= 4;
44 
45     if (point_mask & mask)
46       seg_mask |= 0x80;
47      
48     mask <<= 1;
49     SEG7_SET(i, seg_mask);
50   }
51 }
52 
53 void SEG7_Decimal(alt_u32 Data, alt_u8 point_mask) {
54   alt_u8 mask = 0x01;
55   alt_u8 seg_mask;
56   int i;
57   seg_mask = 0;
58  
59   for(i = 0; i < SEG7_NUM; i++) {
60     seg_mask = szMap[Data%10];
61     Data /= 10;
62    
63     if (point_mask & mask)
64       seg_mask |= 0x80;
65      
66     mask <<= 1;
67     SEG7_SET(i, seg_mask);
68   }
69 }


1行

#include "system.h"
#include
"alt_types.h"
#include
"io.h"
#include
"SEG7.h"


將原來的include改成如上所示。io.h定義了IOWR()。

hello_world.c / C

1 /* 
2 (C) OOMusou 2008 http://oomusou.cnblogs.com
3 
4 Filename    : hello_world.c
5 Compiler    : Nios II gcc
6 Description : Demo how to display 7 seg. on DE2-70
7 Release     : 10/20/2008 1.0
8 */
9 #include <stdio.h>
10 #include "system.h"
11 #include "unistd.h" // usleep()
12 #include "SEG7.h"   // SEG7_Hex()
13 
14 int main() {
15   int i;
16   for(i = 0; i != 100; i++)  {
17     usleep(1 * 1000 * 1000);
18     SEG7_Hex(i, 0x10);
19   }
20 }


使用SEG7_Hex()從1數到100。

完整程式碼下載
DE2_70_NIOS_10_seg7.7z

Conclusion
七段顯示器是大家常用的debug工具,無論是寫Verilog或是寫C,利用友晶提供的TERASIC_SEG7 ip,我們也可以在Nios II利用C控制七段顯示器。

See Also
(原創) 如何在Nios II顯示8位數的七段顯示器? (IC Design) (DE2) (Nios II)
(原創) 哪裡有DE2-70的Nios II reference design可以參考? (SOC) (DE2-70) (Nios II) (SOPC Builder)

系统分类: CPLD/FPGA  |  用户分类: FPGA  |  标签: 无标签  |  来源: 无分类  | 

点击查看原文

发表评论 阅读全文(189) | 回复(0)

发表于 2009/12/6 10:45:03

0

关于投票

8051 IP核的应用开发系统研究

摘要:随着片上可编程系统SOPC技术的日趋成熟,利用IP核重用技术设计可定制的微处理系统使得嵌入式系统设计变得简单灵活,本文介绍了8051 IP核的设计过程,提出了以8051 IP核为基础的MCU片上系统解决方案,通过对步进电机的细分控制,验证了IP核重用技术的灵活性。
关键词:8051 IP核,FPGA,步进电机, 细分

引言

   随着微电子工艺技术和IC设计技术的不断提高,片上系统(SOC)的规模越来越大,开发具有自主知识产权的IP核(Intellectual Property)具有广泛的应用前景。采用IP核的集成复用技术来设计片上系统,能大幅度减轻设计人员的负担,优化系统设计,尤其在系统开发的前期,利用IP核可以对系统进行整体的功能测试,将模块进行裁减组合以优化选择最终的设计方案。Xilinx的MicroBlaze和Altera的NiosII等CPU核已经为人熟知,而Intel公司的MCS51系列单片机是至今为止应用最普及,最广泛,而且很成熟的微处理器,因此建立8051 的可综合IP 核对于各种嵌入式系统和片上系统的应用具有重要意义。

步进电机是靠给步进电机的各相励磁绕组轮流通以电流,实现步进电机内部磁场合成方向的变化来转动的电脉冲-角位移转换元件。传统的步进电机控制通常使用51硬件芯片控制,受硬件限制较多,且系统缺乏灵活性,无法灵活定制。本设计结合应用,定制了8051 IP核作为主控制模块,接入设计的外围硬件电路, 实现了对步进电机的细分控制。

1.8051 IP核设计

1.1  8051 IP CORE的结构

本设计采用的8051 IP核是在Oregano Systems公司提供的免费8051 IP核的基础上定制。代码用VHDL硬件描述语言编写。结合本设计对步进电机的应用,定制其主要模块:控制单元、算术/逻辑运算单元、输入输出口、16 位的定时/计数器、中断控器、特殊功能寄存器、4 KB的程序ROM、128B的数据RAM 等,而串口,EA,PSEN等口线的设计被裁减掉了,其内部结构框图如图1 所示。

图1:8051 IP核的内部结构图

其组成部分及各部分的功能如下:

(1)运算部件模块。主控制器模块控制数据从寄存器和输入端口到ALU,在运算部件中实现数据的算术/逻辑运算。

(2)定时/计数器模块。包含2个定时/计数器,有4种工作模式,与工业标准的8051兼容,但定时时钟频率在内部为clk/16(标准8051是clk/12) 。

(3)中断控制器模块。提供了4个中断源:2个外部中断请求INT0和INT1 ,2个定时/计数器T0和T1的溢出中断请求。

(4)DRAM 数据存储器单元(Data RAM) 。即128 B通用寄存器的RAM 实现,该单元在8051 IP核中用寄存器组来描述实现。

(5)PROM 程序存储器单元( Program ROM) 。片内程序存储器容量为4 KB 可扩充至64 KB ,视需要和所选FPGA 芯片而定。

(6)主控制器模块。它是整个8051 核的控制核心,其中还包括程序计数器PC、堆栈、指令译码器及微指令寄存器等。

1.2  8051 IP CORE设计流程

IP核使用VHDL硬件描述语言编写,将整个系统按模块进行划分,可以进行独立的仿真综合验证,其设计流程图如图2所示:

图2:8051 IP核的开发流程图

(1)首先,根据系统需要定制IP核基本模块,使用Synplify Pro综合器对此IP核进行综合,FPGA芯片选择Altera公司Cyclone系列的EP1C6Q240C8,编译综合成功生成可调用的MC8051_top.Vqm文件,用于在Quartus II环境中生成原理图文件进行调用。

(2)在Quartus II开发环境下,建立此IP核的应用工程,工程名为MC8051_MOTO,在此工程中利用定制我们需要的符合我们所用FPGA芯片的ROM,RAM和扩展RAM,大小分别为4K,128B,和2K。利用QuartusII提供的MegaWizard Plug-In Manager工具定制ROM等存储模块,ROM中的内部结构是由我们编写的软件程序来决定的,将Keil C51编译软件程序,并生成ROM中的内部程序,这种程序是ASCII码或者十六进制形式的文件(.Hex或者.mif)写入的。在工程中建立顶层文件,将生成的8051IP核模块调用,经Quartus II 综合编译后,观看时序分析报告,其最高运行频率为18.05MHz(每次编译都可能不同,I/O 分配不同结果可能不同),因此系统时钟不能超过时序报告的时钟最高频率(即fmax)。在24M的时钟频率下,定制锁相环,使输出频率为18M。

1.3  8051 IP核与传统8051芯片的性能比较

(1)时钟信号输入方式不同,传统8051芯片需外界晶体震荡器,这里直接利用单路的时钟信号即可。

(2)传统芯片中ALE,EA,PSEN等口线在IP核设计中裁减掉了,因为IP核中的I/O口都没有复用,完全使用独立的输入输出方式。总共有64根I/O线,其中P0口可以通过开漏三极管输出变成双向口,P1,P2,P3可以通过上拉电阻实现准双向口,但不具备传统的特殊功能引脚。

(3)传统8051芯片的定时时钟频率为CLK/12,而8051IP核的定时时钟频率为CLK/16,且定时器可扩展,最多可以扩展到128个。

(4)8051 IP核设计了独立的串口读写控制传输引脚,可以通过此独立串口与外界通信。

(5)8051 IP核ROM和RAM的设计,利用Maxplus II或QuartusII提供的MegaWizard plugin Manager工具,该工具所提供的RAM和ROM例化设计文件,实现了128B内部RAM和4KB内部ROM模块,其中ROM模块是一个空结构实体,在有内部程序时换成相应的结构,内部程序必须以ASCII码形式或十六进制形式的文件(.mif文件)写入。

(6)8051IP核的目标代码与工业标准的8051微处理器兼容,但其多数指令周期只有4个时钟周期,比标准8051指令要快。

2.8051 IP核对步进电机的细分控制

为了验证所定制的8051 IP核的功能,本文采用8051 IP核作为主控制模块,设计了步进电机细分控制系统。

2.1 步进电机细分原理

步进电机的驱动是靠给步进电机的各相励磁绕组轮流通以电流,实现步进电机内部磁场合成方向的变化来使步进电机转动的。当步进驱动器接收到一个脉冲信号,它就驱动步进电机按设定的方向转动一个固定的角度,称为步距角。步进电机的细分即对步距角的细分。由于步进电机的转动是对应各相励磁绕组所通以的电流,所以可以通过控制给定电流的大小,来控制步进电机每转动一次的角度。在每次输入脉冲切换时,不是将绕组电流全部通入或切除,而是只改变相应绕组中额定的一部分,则电机转子的每步运动也只有步距角的一部分。这里绕组电流不是1个方波,而是阶梯波,额定电流是台阶式的投入或切除。电流被分成多少个台阶,转子就以同样的个数转过1个步距角。本设计采用三相步进电机,图3为细分后输入各相的阶梯波。

图3:细分后阶梯脉冲波形

如图所示,在选定所需细分数后,只要给在励磁绕组通以对应的阶梯波,即可实现对步进电机步距角的细分。本设计采用广泛使用的恒频脉冲调宽细分驱动技术,通过写入8051 IP核的软件控制程序,实现对步进电机的细分。

2.2系统设计

  本细分控制系统的由四个主要模块组成:定制的8051 IP核,LED显示模块,键盘控制模块,步进电机细分驱动模块。图4为系统结构原理图。

点击看大图

图4:系统结构原理图

 系统设计如下:

(1)首先利用MegaWizard Plug-In Manager工具,将由程序生成的HEX文件初始化到定制的4K ROM单元中。

(2)利用键盘,向系统输入细分数,转动速度等初始化信息。同时,实时控制步进电机的转动速度、方向。速度和细分数,同时在8位LED数码管上显示。速度可调为:0,50,100,200。每按一次加速,速度进阶。细分数可为:2分度,3分度,4分度……100分度。

(3)8051 IP核收到串口控制信号,生成显示信号,发送给LED显示模块。8051 IP核输出P0_o口作字形码输出,P2_o口外接74LS04作位选扫描。同时,根据细分数,查找分度表,将对应数字信号发送给D/A转换器,D/A转换器根据对应数字信号输出阶梯电压Vout, Vout与电压比较器同相端相接 ,而步进电机该相输出电压V,并与电压比较器反相端相接,进行电压比较。当V>Vout时, 电压比较器输出低电平,D触发器清零,开关管组成的功放级截止,I1因绕组能量泄放而下降,出现V<Vout时,电压比较器输出高电平,CP脉冲的上升沿使D触发器的Q=1,功放级导通,则绕组电流I1上升,结果是V>Vout,又 使电压比较器输出低电平,D触发器清零,功放级截止,I1因绕组能量泄放而下降, 又出现V<Vout。此过程一直往复。由于恒频脉冲频率较高,使V 基本保持在Vout值,且I1波顶比较平稳。这样通过D/A转换输入不同的阶梯电压,产生不同的阶梯电流,达到了步距角细分的目的。

3.结论

    IP 核应用领域的不断扩展,可编程芯片的规模化,从而使得将数字电子系统集成到一块芯片上变成可能,同时IP 核的重用性,使得开发风险降低,周期变短。本文利用现有的8051 IP核技术,对其进行相应的定制和裁减,实现了一个片上可编程系统的典型模型,而且可以利用IP 核的可修改,可编程等功能,实现具体要求的片上系统,是片上系统开发的一个有效方案。


本文作者创新点:本文利用IP重用技术,用FPGA设计出8051 IP软核,并将其应用到自动控制系统中,结合步进电机的控制原理,实现了利用8051 IP核作为主控制器的步进电机细分控制系统。在IP核重用技术方面提出了新的思路和解决方法。

系统分类: CPLD/FPGA  |  用户分类: FPGA  |  标签: 无标签  |  来源: 无分类  | 

点击查看原文

发表评论 阅读全文(203) | 回复(0)

发表于 2009/12/6 10:42:06

0

关于投票

基于NIOS II的导航系统平台的设计

引言

  目前广泛应用的MIMU/GPS组合导航系统的实现形式,依应用领域的不同而复杂多样,但是导航计算机板卡负责的工作则相对固定,其主要包括:采集各路传感器输入信号;滤波、融合计算;将计算结果输送给机电控制子系统;提供各种人机交互接口,如LCD,键盘等。

  长期以来,针对各种应用领域或相同领域的不同场合,由于对控制计算能力、接口电路数据吞吐能力等要求的差异,我们习惯于把功能相对固定的导航计算机子系统设计成不同的实现形式,这就造成了对硬件重复研发,相应软件重复调整等低效率现状。

  SOPC(System On Programmable Chip)技术是Altera公司提出的一种灵活高效的SOC解决方案。它的宗旨是将处理器、存储器、I/O口、硬件协处理器或加速器、一般的用户逻辑等系统的设计需要的功能模块都集成到一个FPGA芯片里,构建一个可编程的片上系统。它具有硬件上灵活裁剪、扩充和在线升级的优点,而且市场上有丰富的IP 核资源可选,能成功地解决上述问题。

  1.组合导航系统硬件电路的实现

  硬件框图如图1所示,它主要包括以Nios处理器为主体的片内逻辑(图中虚线包围部分,下文简称片内逻辑)、MIMU与GPS数据采集电路和人机交互接口电路三个部分组成。

  1.1片内逻辑的设计

  本文采用了Altera公司Cyclone系列FPGA EP1C12Q240、NIOS软核处理器及其开发和仿真工具(包括 SOPC Builder,DSP Builder,Simulink,Quatus II等)。在设计中利用的IP核里,比如Nios核,片内Boot ROM,用于FIFO的片内双口RAM,定时器,Avalon片上总线,Avalon三态总线桥,SDRAM接口,JTAG UART等都来自SOPC Builder软件,在此不必赘述。下面重点讨论其他IP核及其接口电路的设计和功用。

点击看大图


  图 1 基于Nios的SOPC组合导航系统设计框图

  6 DSP协处理器 通过定制一些传统的DSP运算指令或反复出现的计算密集型算法指令,来硬件加速CPU的处理能力。IP核可以通过硬件描述语言自己编写,也可以借助Simulink和DSP Builder来辅助实现。

  7 UART 基于RS232通信协议的串行通路接口。UART-0负责传递主控设备的命令(如复位、初始化等)、输入主控设备提供的电子地图的库信息,输出处理结果等。UART-1则负责导入GPS OEM板的数据。该IP核来自于SOPC Builder软件。

  8 A/D接口 除了片选信号,A/D接口时序基本遵循SPI协议,因此选用了SOPC中相应的IP, 而对于片选信号,在系统中额外添加一个通用I/O口来控制之。这样每次对A/D的操作分两步进行:先置低GPIO,再进行SPI操作。

  9 同步采样控制逻辑 负责控制MIMU和GPS信号的同步采集,为数据融合提供准确的输入。该IP核由设计者自行编制,详述请见MIMU和GPS信号采集系统的设计部分。

  10 VGA控制 基于Avalon流模式的VGA控制器。它主要由VGA时序发生器,FIFO存储器,Avalon流模式接口组成。该IP由设计者用VHDL语言自行编制,人机接口部分将详述之。

  11 ATA桥 连接CF卡,保存电子地图信息库、中英文字符点阵库等海量信息。该IP核来自于SOPC Builder软件。

  12 GPIO 最常规的外设控制接口,本系统的LCD、LED、键盘都是采用该接口进行连接,时序上的驱动控制则是由软件实现的。该IP核来自于SOPC Builder软件。

  13 ASMI EPCS4系列配置芯片的专门接口。该IP核来自于SOPC Builder软件。与之相连的Flash存贮空间中有如下内容:一部分是FPGA的配置文件。另一部分作为常规程序存储器用。采用此方案可以省去片外专门的程序存储Flash,充分利用了配置芯片的资源。由于串行器件的带宽限制,我们可以通过将主程序装载入SDRAM中运行来提高程序的运行速度。

  1.2 MIMU和GPS信号采集系统的设计

  MIMU的信号采集工作由微型惯性测量组合、采样/保持器AD1154、多路开关MAX4540、A/D 转换器完成;而GPS的信号采集工作则主要由GPS接收机完成。接收机采用了Jupiter OEM 板,可输出位置、速度、伪距、伪距率、载波相位、卫星星历等数据。系统启动期间,主控设备通过UART-0向片上逻辑发送命令并获取信息反馈,对系统导航参数进行初始化;接收的初始化数据可由片上逻辑的UART-1传递给GPS接收机,以实现GPS的快速初始化和快速锁定卫星.

  我们所讨论的MIMU和GPS信号的同步,是指需要同步的两个数据源在原始信息更新时刻对齐,而不是在经过计算或A/D转换延时等不同通信路径传输后,在输出结果的时刻对齐。GPS接收机解码转换后输出的秒同步脉冲(1PPS,每秒一个脉冲)是与UTC秒点对齐的。接收机严格地在每个1PPS脉冲边沿进行一次伪距、伪距变化率、载波相位、GPS 标准授时、定位等测量,其脉冲沿为GPS数据更新时刻。我们把1PPS脉冲接入FPGA中,由同步采样控制逻辑保证脉冲到来的同时产生一个SSP(同步采样脉冲,synchronous sampling pulse),实现MIMU和GPS数据在整秒时刻同步。当然,MIMU数据更新率远小于1秒,我们可以把1PPS脉冲作为FPGA内部的1秒定时器的标准同步触发时刻,通过逻辑倍频产生相应频率的SSP输出。在GPS信号丢失的情况下,FPGA内部的秒定时器则作为MIMU采样信号的时基标准。

  1.3人机交互接口的设计

  七段数码管负责标识系统的工作状态;而键盘除了作为初始化参数输入的备用接口外,还可以负责切换LCD、VGA显示器等的显示模式;液晶屏则相应地显示输入与输出的导航参数;VGA接口形象的输出电子地图背景、车辆当前位置及运行轨迹等信息。

  excalibur.h 头文件定义了七段数码管、按键数据结构指针na_seven_seg_pio 和na_button_pio通过对指针所指PIO数据结构内的np_piodata数据寄存器操作,来让数码管显示特定的字符或判断是否有按键按下,以及是哪个按键。

  本文采用型号Optrex 16027的LCD屏,头文件pio_lcd16027.h定义了九个控制子程序,通过这些程序完成对LCD的控制。标准VGA画面大小是640*480,每秒60帧左右。像素时钟高达25.175MHZ。如果每个点都由Nios软件扫描实现,那么在40ns的间隔内,最多能让共作在50MHZ的CPU执行两条指令。所以,我们采用DMA控制器在流模式VGA控制器和SRAM之间建立一条DMA传送通道,让硬件完成像素信息的自动读取,缓解了CPU的工作压力。VGA时序发生器的设计源程序由VHDL语言实现,下面是部分示意代码:

点击看大图


  2.系统工作原理

  系统上电后,串行配置器件EPCS4配置FPGA;然后NIIOS启动,运行片内ROM中的Bootloader。Bootloader根据选择端的控制选择工作模式,模式分为两种:调试模式和运行模式。在调试模式下,Bootloader启动GERMS监控程序,我们可以对系统进行开发调试。在运行模式下,Bootloader将EPCS4中存储的主程序装载到SRAM中全速运行。然后,程序指针复位指向SRAM中的系统主程序。主程序先初始化并配置系统,然后开始正常工作。

  3.软件设计

  由于本控制系统架构庞大,我们在软件设计时使用实时操作系统microC/OS作为软件内核。该操作系统具有内核小,代码公开等优点,而且Altera公司提供了关于此系统移植方面比较详细的技术文档,操作起来简单易行。系统软件分为三个层次设计:一、驱动层。主要包括了UART驱动,LED驱动,键盘驱动,LCD驱动,VGA驱动,SPI总线设备驱动等等。二、内核层。包括系统任务和内核调度。三、应用层。

  任务主要有数据采集任务,数据融合任务,数据滤波任务,导航计算任务,显示任务等。其中还有一些用于控制管理性质的任务,包括错误捕捉任务及其相应的处理方程序等。

  系统的核心是操作系统的内核调度,负责整个软件的运作。系统相关的层面是以任务为单位的系统模块,这些任务模块负责市实现导航系统的正常运行,负责系统模块的配置控制和差错检测,响应处理用户的操作。硬件相关的层面以驱动任务为单位,它们作为操作系统和硬件系统中介,直接负责对硬件设备的驱动控制。软件分层封装,用任务调度的方法来实现,可以提高软件设计的效率,降低设计风险,利于移植和升级。

  4.结论

  NIOS符合工业技术的潮流,即硬件设计软件化。此设计方法可以对硬件做全面细致的模拟仿真,减少硬件设计的错误,有效降低了开发成本,增强了产品的竞争力。而且由于它属于单片解决方案,不仅提高系统的鲁棒性,还可以有效地保护开发者的知识产权。

系统分类: CPLD/FPGA  |  用户分类: FPGA  |  标签: 无标签  |  来源: 无分类  | 

点击查看原文

发表评论 阅读全文(126) | 回复(0)

发表于 2009/12/5 22:32:05

0

关于投票

基于Nios 软核处理器的七段数码管动态显示设计

       SOPC(System On Programmable Chip)技术是美国Altera公司于2000年最早提出的,并同时推出了相应的开发软件Quartus II。SOPC是基于FPGA解决方案的SOC(System On Chip),构成SOPC的方案也有多种。第一种是基于FPGA嵌入IP硬核的SOPC系统,即在FPGA中事先植入嵌入式系统处理器,目前最常用的嵌入式处理器大多采用了含有ARM的32位知识产权处理器核的器件。第二种是基于FPGA嵌入IP软核的SOPC系统,目前最有代表性的软核处理器分别是Altera公司的Nios II核,以及Xilinx公司的MicroBlaze核。第三种是基于HardCopy技术的SOPC系统,HardCopy就是利用原有的FPGA开发工具,将成功实现于FPGA器件上的SOPC系统通过特定的技术直接向ASIC转化。

1 基于Altera公司NiosⅡ软核处理器的SOPC系统

Altera公司Nios II软核是目前使用最为广泛的一种软核处理器。值得一提的是,利用Matlab和Altera公司的DSP Builder,用户可以为Nios II软核处理器设计各类DSP硬件加速器,并以指令的方式加入Nios II的指令集,从而可以构建自己的DSP处理器系统。

1.1 基于NiosⅡ软核处理器的SOPC系统结构

如图1所示的一个基本的基于NiosⅡ软核的SOPC系统,除NiosⅡ核、定时器和片上存储器以外,还需要在FPGA器件中添加一些接口元件。这些元件一方面通过片上的Avolon总线与NiosⅡ软核相连,另外一方面又提供了外设与NiosⅡ软核通信的接口界面。



Altera公司QuartusⅡ软件中的SOPC Builder工具提供了许多常用的外设接口元件,如UART接口元件、PIO接口元件等,通过这些接口元件可以连接诸如RS232、LED、数码管和按键等输入输出设备。在相对复杂的系统设计当中,还可以通过Avalon三态总线桥外接大容最的SRAM和FLASH,以提供更大的程序和数据存储空间。从图1中,还可以注意到,通过使用系统提供的用户自定制外设接口元件的功能,用户可以在系统中添加一个符合Avalon总线规范的外设接口元件,以连接用户特定功能的外部设备。

1.2 自定制Avalon用户外设接口元件简介

对于自定制的Avalon外设接口元件按照Avalon总线操作的不同可以分为两类:Avalon Slave外设接口元件型的自定制的Avalon Slave外设接口元件框图。从图2中可以看到寄存器的定义是自定制外设接口元件很重要的一部分,必须根据设计的需要确定寄存器的个数和种类。图2中的Avalon Slave接口提供了自定制外设接口元件与NiosⅡ处理器之间数据交换的界面,其接口信号类型也必须根据设计的需要合理地进行选择。常用的Avalon Slave接口信号类型有:clk,chipselect,address,write,writedata,byteenable,reset等。图2中的任务逻辑具体说明了自定制外设接口的功能,并给出了与外设连接的接口信号。



自定制Avalon Slave外设接口元件的方法:可以利用SOPC Builder提供的元件编辑器在图形用户界面下将用硬件描述语言(Verilog或VHDL)描述的用户逻辑封装成一个SOPC Builder元件。相应的硬件描述语言文件给出了自定制外设接口元件的内部寄存器结构,使用到的Avalon Slave接口信号和自定制外设接口的逻辑功能。一旦定制成功后,用户自定制的外设接口就可以象SOPCBuilder中其他元件一样被调用。

     

2 基于NiosⅡ软核处理器的七段数码管动态显示设计

数字系统设计中,用数码管显示数据结果是常用的一种方法。利用Altera的SOPC Builder工具进行Nios Ⅱ系统设计时,并没有提供专门的数码管显示接口元件,但可以使用PIO元件驱动数码管显示,不足之处是占用器件引脚数目过多。本文当中以自定制Avalon Slave外设接口元件的方式,给出了一种基于NiosⅡ软核的七段数码管动态显示设计方案。该设计可以用来驱动1~8个共阴极(或共阳极)数码管的显示,可以根据需要选择小数点显示的位置,每个数码管可以显示0~F之间的十六进制字符。

图3为自定制的数码管动态显示接口元件逻辑结构图,其中定义了2个寄存器display_data_reg和controlreg。display_data_reg是个一个32位二进制的数据寄存器,其数据每4位可以译码得到1个数码管的七段显示所需的字符码,因此,display_data_reg同时最多可以给出8个数码管所需要的显示数据。control_reg是一个8位二进制的控制寄存器,但只定义了0~2位和第4位的含义。0~2位的数据给出了小数点显示的位置,数值范围在“000”~“111”之间,对应着8个数码管最低位到最高位的小数点的位置。第4位是数码管显示的启动停止位,当该数据位为1时,可使自定制接口元件所驱动的数码管正常显示结果;当该数据位为0时,停止显示,所有被驱动的数码管熄灭。

参数n定义了循环加法计数器的模数,同时也决定了驱动数码管显示的个数,其取值范围在1~8之间。clkdisplay是循环加法计数器的时钟输入,他决定了计数器的计数频率,同时也决定了数码管显示的动态扫描频率。参数pos用于决定驱动数码管的类型,其值可设定为0或1。当其值为0时,seg_out字符码输出高电平有效,bit_control数码管位选控制输出低电平有效,此时输出结果用于驱动共阴极数码管显示;当pos值为1时,seg_out字符码输出低电平有效,bit_control数码管位选控制输出高电平有效,此时输出结果用于驱动共阳极数码管显示。

seg_out为自定制元件的字符码输出,用于驱动数码管显示(包括小数点位)。其中,最高一位seg_out[7]用于驱动对应数码管的小数点显示,低7位seg_out[6..0]用于驱动数码管的七段宁符显示。图3中数码管七段译码器根据循环加法计数器的当前状态值,从display_data_reg寄存器中选择4位二进制数据进行译码。例如,当前驱动的数码管的个数为5个(即n=5),循环加法计数器的当前状态值用count表示,则count在0~4范围内变化;若计数器的当前状态值count为2,则选择寄存器display_data_reg[11..8]的4位二进制数据进行译码,若计数器的当前状态值count为3,则选择寄存器display_data_reg[15..12]的4位二进制数据进行译码,即总是选择寄存器display_data_reg[(count+1)×4-1..count×4]的4位二进制数据进行译码。寄存器control_reg的低3位指明了小数点显示的位置,如control_reg[2..0]的值为“000”,则第0位数码管的小数点点亮,若control_reg[2..0]的值为“010”,则第2位数码管的小数点点亮。因为,循环计数器的状态值count反应了数码管动态显示过程中当前数码管显示的位皆,因此,数码管小数点译码器只要比较control_reg[2..0]与count的值,若两者相等,seg_out[7]输山有效值(共阴极输出为高电平,共阳极输出为低电平)即可驱动对应数码管的小数点点亮。

bit_control为自定制元件的位选控制输出,其数据宽度为n位二进制,与要驱动的数码管的个数是一致的。上面已经提到,循环加法计数器的状态值count反应了当前数码管显示的位置。因此,只要根据count的值,使得bit_control对应位输出有效值即可。例如,n取值为5,pos取值为0(即驱动共阴极数码管),若计数器的当前状态值count为2,则bit_control的输出结果为“11011”,若count为4,则bit_control的输出结果为“01111”。


      

自定制元件的设计采用的是VHDL语言,其实体描述如下面程序所示:



从上面的程序可以看到:n和pos定义成了类属变量,当完成接口元件的定制以后,类属变量在自定制元件的设置窗口中将以用户参数的形式出现,如图4所示,用户可以设置其值。



实体描述当中除定义了自定制元件与外部设备的接口信号clk_display,seg7_out,bit_control信号以外,还定义了 Avalon Slave接口信号,NiosⅡ软核通过这些信号访问自定制元件中定义的寄存器。前面介绍的两个寄存器display_data_reg和control_reg是在程序的结构体说明部分定义的,具体语句如下:

signal display_data_reg:std_logic_vector(31downto 0);
signal control_reg:std_logic_vector(7 downto 0);

结构体中还完成了所定义的两个寄存器的数据写入操作。图3中所示的模n循环加法计数器、七段译码器、小数点译码器和位译码器也在结构体中按上面所介绍的功能设计完成。

3 实验结果

为了验证用于驱动七段数码管动态显示的自定制元件功能,实验中使用SOPC Builder建立了一个最简单的NiosⅡ系统。该NiosⅡ系统添加了3个元件,名称为cpu_0的NiosⅡ软核处理器;名称为seg7的自定制元件,用于完成数码管的显示驱动;名称为onchip_RAM的片上随机存储器,存放调试时的程序代码以及用作程序运行空间。生成的NiosⅡ系统的图形符号如图5所示,clk是系统工作时钟输入;reset_n是系统复位输入,低电平有效;clk_display_to_the_seg7是数码管扫描时钟输入,他决定了数码管动态显示的扫描速度;bit_control_from_the_seg7是位选控制输出,决定了动态过程中哪一个数码进行显示;seg7_out_from_the_seg7是数码管显示数据输出,决定了数码管显示的内容。

新建顶层原理图,调用该NiosⅡ系统,为其添加输入输出引脚,并定义引脚号,选择目标器件型号为EP1C6Q240C8,编译生成配置文件,并通过下载电缆下载到目标器件中。接下来利用NiosⅡIDE建立用户程序。



实验建立NiosⅡ系统时,添加驱动七段数码管显示的自定制元件seg7时的参数n和pos(如图4所示)设置成了两种测试情况,分别用来验证其驱动共阴极和共阳极数码管显示的情况。第一种测试情况将n设置成7,pos设置成0,用来驱动7个共阴极数码管显示。NiosⅡIDE建立的用户测试程序如下:



程序编译通过后,可以在硬件中调试运行程序。为了便于观察测试结果,在ModelSim中运行仿真结果,得到仿真波形如图6所示。仿真分析时系统工作时钟(clk)设置为了50 MHz,数码管动态显示扫描频率(clk_display)设置为1 kHz。图6(a)给出了寄存器内容的写入过程,3个write高电平期间完成了 3次寄存器的写入操作。第一次write高电平将0x00写入address为1的寄存器(即控制寄存器,该定义是在自定制元件的硬件描述语言设计中完成的);第二次write高电平将0xAF05163写入address为0的寄存器(即数据寄存器);第三次write高电平将0x13又写入address为1的控制寄存器。当控制寄存器的内容为0x00时,数码管是停止显示的,因此,在共阴极显示的情况下bit_control的输出全为高电平,直到控制寄存器的内容写入0x13后,bit_control才有输出为低电平的情况(如图6所示)。图6(b)给出了写入寄存器内容以后的工作情况,当数据寄存器写入0xAF05163、控制寄存器写入0x13后,bit_control将从1111110到0111111循环变化,同时将数码管显示所需要的字符码从seg7_out输出。如当bit_control为1111110时,seg7_out输出字符码为0x4F,对应显示“3”;当bit_control为1111101时,seg7_out输出字符码为0x7D,对应显示“6”。由于控制寄存器写入的内容为0x13,即第三位数据管的小数点会亮起,因此当bit_control为1110111时,seg7_out输出字符码为0xED(即二进制的“11101101”),数码管对应显示“5”,而最高一位的“1”会让该数码管的小数点点亮。

    

以上是第一种测试情况。第二种测试情况是将seg7的参数n设置成5,pos设置成1,用来驱动5个共阳极数码管显示。NiosⅡ IDE建立的用户测试程序如下:



程序编译通过后,同样在Modelsim中运行仿真结果,得到仿真波形如罔7所示。仿真分析时系统工作时钟(clk)设置为了50 MHz,数码管动态显示扫描频率(clkdisplay)设置为1 kHz。



与第一种共阴极显示情况相比,第二种共阳极显示时的寄存器写入过程是大体一样的。不同之处在于共阳极显示时的bit_control和seg7_out和输出极性正好与共阴极显示时的相反。

通过以上的实验,验证了自定制七段数码管动态显示接口元件功能的正确性。

4 结 语

在用Altera公司的SOPC Builder工具完成NiosⅡ软核SOPC系统设计时,可以用SOPC Builder中提供的元件来构建整个系统。但对于有些外部设备,SOPC Builder并没有提供对应的接口元件,此时,就可以使用SOPC Build-er工具的自定制用户元件功能来创建特定功能的接口元件。在本文中,针对数码管的显示,定制了一个七段数码管动态显示接口元件,可以用来驱动1~8个共阴极(或共阳极)数码管的显示,可以根据需要选择小数点显示的位置,每个数码管可以显示0~F之间的十六进制字符,并通过实验验证了其功能的正确性。

系统分类: CPLD/FPGA  |  用户分类: FPGA  |  标签: 无标签  |  来源: 无分类  | 

点击查看原文

发表评论 阅读全文(179) | 回复(0)

发表于 2009/12/5 18:48:49

0

关于投票

quartus ii 管脚映射

管脚映射有两种方法

(1)在" Assignment"中选择"Pin Planner",之后在location选项中挨个选择,当然这需要花一定的时间如果你的管脚比较多的话。

(2)用TCL脚本一次性的分配管脚

步骤:

a)Project 下选择generate TCL file for project

b)将文件中带有set _location_assignment指令,并且-to 后面的参数和程序中用到的管脚名对应。

PIN_V14是FPGA的管脚,HEX0[5]是程序中定义的管脚

格式如下:set_location_assignmentPIN_V14-toHEX0[5]

编辑完成之后保存

c)Tool 菜单下选择Tcl Scripts

选择刚才的TCL之后run就ok了

系统分类: CPLD/FPGA  |  用户分类: FPGA  |  标签: 无标签  |  来源: 无分类  | 

点击查看原文

发表评论 阅读全文(156) | 回复(0)

发表于 2009/12/5 17:12:57

0

关于投票

nios II 实验五 数码管显示数字钟(定时器实现 外部中断)

nios II 实验五 数码管显示数字钟(定时器实现 外部中断调节)

 

#include "system.h"                      //包含基本的硬件描述信息
#include "altera_avalon_timer_regs.h"    //定义内核寄存器的映射,提供对底层硬件的符号化访问
#include "altera_avalon_pio_regs.h"      //包含基本的I/O口信息 
#include "alt_types.h"                   //Altera定义的数据类型
#include "sys/alt_irq.h"                 
//#include "sys/alt_alarm.h"             //系统时钟服务头文件
#include "unistd.h"                      //延时函数usleep

//定义端口
#define seg  *(volatile unsigned char *) SM_SEG_BASE
#define bit  *(volatile unsigned char *) SM_BIT_BASE
#define key  *(volatile unsigned char *) KEY_BASE

//函数声明
void Timer_Init();
void Timer_ISR(void* context, alt_u32 id);
void display();
void KeyDown_ISR(void* context, alt_u32 id);
void KeyDown_Init();

//变量定义
alt_u8 duan[11]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,0xBF};
alt_u8 num[8] = {0,0,0,0,0,0,0,0};
alt_u8 second,min,hour;

//按键中断服务函数
 void KeyDown_ISR(void* context, alt_u32 id)
{
     if(key == 0x06) { second = 0;  while(key == 0x06){display();} }                     //秒调设置
     if(key == 0x05) { min++; if(min==60) min = 0;  while(key == 0x05){display();} }     //分调设置
     if(key == 0x03) { hour++; if(hour == 24) hour = 0;  while(key == 0x03){display();} }//小时设置

     IOWR_ALTERA_AVALON_PIO_EDGE_CAP(KEY_BASE, 0x00);   //清中断捕获寄存器
}

//按键中断初始化
void KeyDown_Init()
{
    IOWR_ALTERA_AVALON_PIO_IRQ_MASK(KEY_BASE, 0x07);   //开KEY中断
    IOWR_ALTERA_AVALON_PIO_EDGE_CAP(KEY_BASE, 0x00);   //清中断捕获寄存器
   
    alt_irq_register(KEY_IRQ,0,KeyDown_ISR);           //注册中断函数
}

//定时器初始化
void Timer_Init()
{
    alt_irq_register(TIMER_IRQ,0,Timer_ISR);          //注册中断函数
    IOWR_ALTERA_AVALON_TIMER_STATUS(TIMER_BASE, 0);   //清状态标志
    IOWR_ALTERA_AVALON_TIMER_CONTROL(TIMER_BASE, 7);  //启动定时器允许中断,连续计数
}

//定时器中断服务函数
void Timer_ISR(void* context, alt_u32 id)
{
    second++;
    if(second == 60) { min++; second = 0;}
    if(min == 60) { hour++; min = 0;}
    if(hour == 24) { hour = 0;}
   
    if(second % 2) duan[10] = 0xff;
    else duan[10] = 0xbf;              //秒闪烁
   
    IOWR_ALTERA_AVALON_TIMER_STATUS(TIMER_BASE, 0);    //清状态寄存器
}

//数码管显示函数
void display()
{
    alt_u8 j;
    num[0] = second % 10;
    num[1] = second / 10;
    num[2] = 10;
    num[3] = min % 10;
    num[4] = min / 10;
    num[5] = 10;
    num[6] = hour % 10;
    num[7] = hour / 10;
   
   for(j=0; j<8; j++)
    {
       bit = ~(0x01 << j);   //位选低位有效
       seg = duan[num[j]]; 
       usleep(500);  
    }
}

//主函数
int main(void)
{
    KeyDown_Init(); //按键中断初始化
    Timer_Init();        //定时器初始化
    while(1)
    {
        display();  //显示
    }
    return 0;
}

系统分类: CPLD/FPGA  |  用户分类: FPGA  |  标签: 无标签  |  来源: 转贴  | 

点击查看原文

发表评论 阅读全文(184) | 回复(0)

发表于 2009/12/5 15:50:44

0

关于投票

【转】Nios 开发流程 (7位数码管控制)

上个例子中,我们使用VHDL语言,根据FPGA管脚与数码管和按键管脚的连接,通过一系列的语句控制管脚电平的高低,从而让FPGA实现数码管显示功能。可见,对于比较简单的功能实现,可以像这个例子中那样,直接控制最底层资源,甚至对每个管脚在每个时刻的电平输出了如指掌。

       但是,如果设计稍显复杂,那么对底层细节的过多关注就会成为一种累赘。

       试想我们平时在电脑上编写C程序,比如在显示器上输出一行字,我们只用一句printf()即可完成,至于打印命令怎么传到显示芯片上,哪个芯片管脚怎么变化,又怎么传到显示器上输出,诸如此类涉及底层硬件的问题,我们没必要关注太多。于是,我们把用printf()这类高级语言描述设计逻辑的工作称为软件设计。显然,软件只是一种抽象的看不见摸不着的东西,它的结构接近于人类思维逻辑。无论软件再怎样构思精妙,只有在硬件上才能体现出实际效果。

       做计算机开发应用程序的时候,硬件是现成的,软硬件之间的桥梁早就由操作系统给你搭好了,我们只需专心完成软件的构思和设计就OK。

       显而易见,软硬件的分工会给电子设计带来极大的方便,自然有人把这种分工方式引进FPGA设计领域,琢磨着怎么在小小的FPGA上也搞个软硬件协同设计,负责硬件设计的和负责软件的各司其职,最后pia一整合,效率倍增。

       来看看nios是怎么做的。拿出DE2开发板,上面很多外设接口和与之连接的芯片,那是硬件,中间有一块大的CycloneII芯片,里面是空的,等着我们编写程序下载到里面运行,前篇文章我们用最原始的方法写了个数码管控制器,这次我们换种方法,同样是数码管控制器,用软硬件协同设计来完成。

       跟计算机对比,硬件我们有了,软件就用C语言来写,但是nios系统可没提供WinXP,也就是说软件和硬件之间的那座桥还得自己解决。

       看上图,这座桥分为3个层次:硬件控制层,设备驱动层,硬件抽象层(简称HAL)。既然是软硬件的过渡部分,那么这3层的设计需要对硬件和软件都有一定程度的了解,姑且称之为“软硬件混杂设计”吧。

       每一层所要完成的任务,就是整合和简化硬件操作细节,整合,再整合,使其一目了然。

       <1> 硬件控制层

       与硬件直接打交道的是硬件控制层。

       上面提到,搭“桥”的目的是让软件设计人员可以完全忽略硬件操作细节,因此,我们希望所有的硬件细节都能在这层解决,并向设备驱动层提供整齐的“接口”。之前的例子可看作硬件控制器的雏形,但还缺少与设备驱动层的接口。

       何为“整齐”呢?比如说,设计数码管控制器,我想让它显示数字“5”,最好的方法是,我将数据“5”和表示“显示”的命令从设备驱动层传给硬件控制层,直接告诉它:我要“数码管”“显示”“5”。至于要控制哪个管脚电平高低才能显示“5”,全由硬件控制层负责。

       类似这样分工合作的例子在日常生活中屡见不鲜。比如说,邮局要将一封信送给家住A小区的张三,邮递员把信放入A小区的信箱,小区物业再去确认张三的具体住处,把信最终送到张三手中。

       类比可见,邮局相当于设备驱动,物业相当于硬件管理器,张三则是具体的硬件,邮局和物业之间的接口是物业提供的信箱,设备驱动和硬件管理层之间的接口,我们称之为“寄存器”,同样由硬件管理层提供,“寄存器”是两层之间得以明确分工和相互联系的关键。

       设备驱动开发人员眼中的硬件就是一组寄存器的抽象,通过读写寄存器间接控制硬件行为。

        那么,在数码管控制器里加入一个数据寄存器和一个命令寄存器:

       data_reg存储待显示的数据,cmd_reg为‘1’时显示,为‘0’时清空。

       <2> Avalon总线

       你可能会说,这有什么?在每个硬件管理器和设备驱动之间都建立一个通道呗。这是最直接的办法,但显然不是最好的办法。试想,城市为什么要建高速公路呢?多修几十根羊肠小道不也一样能跑车吗?有人回答:为了收养路费呗。$%@&&! 小路上开车,速度慢且不说,管理协调是个大问题,是一条大公路容易管理,还是几十根羊肠容易理顺?

       好了,回到正题,nios系统需要一条“高速公路”,称为“总线”,“总线仲裁器”则行使“交通管理局”的角色,控制数据的进出,并为每个硬件提供一个进出“高速公路”的接口,用“地址”来标识这个接口的位置。nios采用的是Avalon总线,它有着一套接口规范:

       同步时钟 clk
       片选信号 chipselect
       地址 address
       读请求 read
       读传输 readdata
       写请求 write
       写传输 writedata

       这些是比较重要的接口信号,其它的不一一列举了。硬件控制器要接入总线,必须遵循接口规范,就像高速公路出口必须摆个收费站一样。

       那么在在数码管控制器里加入Avalon总线信号:

       既然加入了两个寄存器和avalon信号,就需要对硬件逻辑进行必要改动,大致过程是,当chipselect和write有效时,将write_data赋给address对应的寄存器;当chipselect和write有效时,将address对应寄存器的值赋给read_data。另外,根据这两个寄存器的内容决定数码管输出信号oSEG0。代码不贴出来了,具体见工程压缩包。

       <3> 设备驱动程序

       其实,“总线仲裁器”也可看作一种硬件控制器,只不过它管的不是具体的硬件,而是负责数据的传输。那么它也有自己的设备驱动,封装了总线操作的细节。既然总线是现成的,我们秉承“拿来主义”的原则,甭管它怎么实现的,会用就行。

       例如,数码管设备驱动要把数据“5”和“显示”命令传给数码管控制器,设计两个函数,由于数据和命令的传递必须经过总线,那么需调用总线驱动函数IOWR(基地址, 偏移量, 数据),另外,读取寄存器用到IORD(基地址, 偏移量),这两个函数在<io.h>里。

       <io.h>的路径是"..\altera\kits\nios2_60\components\altera_nios2\HAL\inc"。

       至此,“桥”搭完。

点击看大图

       函数功能从字面上很好理解。刚才定义两个寄存器时,data_reg在前面,所以偏移量是0,cmd_reg在后面,偏移量是1。××_REG_MSK称为掩码,avalon总线数据接口共32位,但我们设计的data_reg位宽是3,cmd_reg位宽为1,掩码的作用在于告知寄存器宽度,知道就行,实际上用不着。××_REG_OFST是寄存器内的偏移量,这里同样用不着,先写上吧。

       OK,我们的数码管设备驱动文件正式出炉了,看看是不是简洁明了很多啊?

       <4> 硬件抽象层(HAL)

       设备驱动程序封装的仅仅是对某个寄存器的一次读写操作,功能单一,需要在硬件抽象层再做一次封装。

      直接将这些函数列出来,一目了然,不作多余的解释了。

点击看大图

       至此,“桥”搭完。

       接下来在把我们的“数码管控制器”加入sopc builder系统中。

       现在几乎所有讲nios的书都会提及自定义用户外设,而且用的都是altera官方提供的例子PWM,本文的“数码管控制器”就是照着它依葫芦画瓢改过来的,呵呵,惭愧惭愧,之所以想改它,一是因为它用的是verilog而不是VHDL,而大多数人先接触却是VHDL;二来PWM的显示效果似乎不太明显,改成数码管显示相对比较有成就感;第三,PWM的逻辑稍微有一点点复杂,我们的重点在于说明怎样自定义外设,当然例子越简单越好。

       既然是照着PWM原样改的,所以本文工程的结构与之保持高度一致,将其加入sopc builder的步骤也差不多,这里我就不再码字了,各位照着书上做吧:
      《SOPC嵌入式系统基础教程(周立功等著)》第8章……

       再接下来,建立一个包含“数码管控制器”的nios系统,并编写应用程序,实现从0到9计数。

       贴张官方的nios设计流程图,看起来很漂亮是吧,不愧是altera的东西,大而全而不乱。

点击看大图

       先说最中间的"SOPC Builder",它的任务是建立一个“以Nios CPU为核心,以Avalon总线为纽带,将各种硬件设备连接起来”的nios系统;这个系统要在FPGA中运行,所以必须挂靠一个Quartus II工程,用左边的Quartus II进行分配引脚等等工作,生成硬件系统;接着,右边的Nios II IDE就可以在这个硬件系统上设计应用程序了;最后将硬件系统和软件程序分别下载到FPGA芯片上,大功告成。

       下面step by step

       <1> Quartus II 新建一个工程名,工程名"DE2_SEG7"。

       <2> "Tool" → "SOPC Builder" 打开SOPC Builder。

       <3> "System Name": nios2_system   选VHDL。

       一个包含“数码管控制器”的最小系统至少由3部分组成:CPU必不可少,RAM存储代码,还有刚才设计的"seg7_avalon"。

       <4> 加入"Nios II Processor",选"Nios II/e",精简型够用了。

       <5> 加入"On-Chip Memory",类型选"RAM",位宽默认"32 bits","Total Memory"选"48Kbytes",等会儿软件要占用四十多K空间。

       <6> 加入"seg7_avalon"。

       <7> 将这三个组件的名称改好看点,然后设定RAM的基地址为"0x00000000",再右键锁定基地址,如图:

点击看大图

       为什么要锁定RAM的基地址为0呢?点选第二个选项卡,可以看到"Reset Address"对应着RAM,系统的复位肯定要从地址0开始。

       <8> 由于刚才人为改动了地址分配,弄乱了,让系统自动再分配一次,当然被锁定的RAM基地址是不会变的。"System" →"Auto-Assign Base Addresses"。最终系统组件列表如下:

点击看大图

       注意,seg7的地址范围是"0x00010800"→"0x00010807",占8个地址,nios系统的地址按字节分配,也就是说,每个字节占用一个地址,数码管控制器中定义了两个寄存器,avalon总线规定每个寄存器占32位(实际上是不是32位它就不管了,反正按最大32位分配),这样两个寄存器共占去8个字节,自然需要8个地址。

       <9> 点击"Generate"生成nios系统,回到Quartus II。

       <10> 新建一个顶层文件"File"→"New"→"Block Diagram/Schematic File",引入nios II系统,增加输入输出引脚。然后,"Assignment"→"Import Assignment",添加引脚分配文件(在DE2光盘目录下的\DE2_tutorials\design_files\DE2_pin_assignments.csv),改动顶层文件的引脚名称使其与.csv文件中保持一致。

点击看大图

       <11> 编译,查看编译报告,可见,48K的RAM占用了芯片83%的memory bits,差不多耗光了。

       <12> 硬件部分已经搞定,关掉Quartus II,打开Nios II IDE,切换到工作目录下。

       <13> "File"→"New"→"C/C++ Application","SOPC Builder System"选择"nios2_system.ptf"(就是刚才Generate Nios II系统生成的东东),再选模板"Hello World"(纯属偷懒),顶上的"name"改成"seg_example","Finish"。

       <14> 改动hello_world.c,代码的功能为:先初始化数码管,等待2秒钟,再进行0-9的循环,循环过程中穿插2秒钟的清屏。SEG7_BASE的宏定义在system.h中,实际上就是在SOPC Builder中的seg7_avalon的基地址0x00010800。

       <15> "Project"→"Build Project",得到编译报告,软件占用了7K空间……

点击看大图

       <16> 下载到DE2板上,运行,数码管不停地闪啊闪。

       OK,从硬件到软件的一条龙讲完了。

系统分类: CPLD/FPGA  |  用户分类: FPGA  |  标签: 无标签  |  来源: 无分类  | 

点击查看原文

发表评论 阅读全文(193) | 回复(0)

发表于 2009/12/3 17:18:41

0

关于投票

nios II标准(Standard)系统的创建(3)

第三节:在QuartusII中使用上述niosII系统
1。在编译完成后。首先在QuartusII中,打开SOPC Builder生成的sopc_ezC6Be_StdF50.bsf,检查一下引脚,看看跟你的设想是否有误,如下图:
 
2。你可以使用上述的sopc_ezC6Be_StdF50.bsf,来构造你自己的系统。如下图,我创建了ezC6Be_StdF50.bdf,来使用它。  
 
3。其中,sdram_pll按照如下图配置,input clk是50M,   
 
请ezNiosC3A,ezNiosC3B,ezNiosC6A的用户按照如下操作input clk是16M:
 
4。如下是delay_reset_block.它的作用主要是延迟reset,以等待PLL稳定,如果要求不严格,也可以不加。  
点击看大图 
5。完成后,选中Processing -> Start Compilation,开始编译。
 
6。编译成功后,可以看一下Compilation Report.其中,Total logic elements使用了45%,还剩余55%可以作为其他用途。
点击看大图 

第四节:下载与测试。
最后,选择Tools ->Programmer,下载整个配置到FPGA中,如下图。  
点击看大图 
下载成功后,可以看到LED的有规律的变化(流水灯)。  

 第五节:运行Hello_World程序。
Hello_World程序似乎经常是许多高级入门教材的第一个范例,我们也来运行一下它。     类似于在第三节中的操作,首先回到Nios IDE中,

1.选择File -> New -> Project,然后选择:Altera Nios II ---  C/C++ Application,然后选择Next 
 
2.Name空栏中,您可以您可以依据需要,为其命名。比如,我为其取名为ezC6Be_StdF50_hello_world_1,完成后,选择Next。(注意,要在Select Project Template 中,选中Hello World)
点击看大图 
3.选中Create a new system library named: ......,最后选择Finish,系统会自动生成该项目。
点击看大图 
4.并不用对hello_world.c进行任何修改。 
 
5.首先选中Project:ezC6Be_StdF50_hello_world_1,然后点击右键,在弹出的窗口中选择System Library Properties,如图:
 
系统会弹出System Library Properties设置对话框,请按照如下图片设置,完成后,选择Apply确认,然后就可以关掉这个对话框了。 
 
6.选择Project -> Build Project,编译整个项目。  
 
7.编译成功后,为开发板(插上USB取电电缆),并将ByteBlasterII下载电缆插在JTAG口,然后选择Run -> Run As -> 1 Nios II Hardware,在实际的硬件上运行上述C程序。
 
7.可以看到nios2-terminal窗口如下显示:Hello from Nios II! 
点击看大图 
到这里就大功告成了,整个试验是比较消耗时间与脑力的,成功后,真的可以好好休息一下了!

系统分类: CPLD/FPGA  |  用户分类: FPGA  |  标签: 无标签  |  来源: 无分类  | 

点击查看原文

发表评论 阅读全文(117) | 回复(0)

发表于 2009/12/3 17:17:37

0

关于投票

nios II标准(Standard)系统的创建(2)

10.为系统添加sys_clk_timer。
双击左边的Other -> interval timer,为系统添加timer,请按照如下图片配置。我把它改名(rename)为sys_clk_timer, 
 

11.为系统添加high_res_timer。
双击左边的Other -> interval timer,为系统添加timer,请按照如下图片配置。我把它改名(rename)为high_res_timer. 
 

12.为系统添加JTAG_UART。
双击左边的Communication -> JTAG_UART,为系统添加JTAG_UART,请按照如下图片配置。
 
 

13.为系统添加RS232_UART。
双击左边的Communication -> UART(RS-232 serial port),为系统添加UART,请按照如下图片配置。ezNiosC3A,ezNiosC3b,ezNiosC6A的用户由于开发板上不带该器件,可以跳过此步。
 
 

14.为系统添加LED_PIO。
双击左边的Other -> PIO(Parallel I/O),为系统添加PIO,请按照如下图片配置。我把它改名(rename)为led_pio。
 

15.为系统添加button_pio。
双击左边的Other -> PIO(Parallel I/O),为系统添加PIO,请按照如下图片配置。我把它改名(rename)为button_pio。
 
 
 

16.为系统添加sysid。
双击左边的Other -> System ID Peripheral,为系统添加sysid,请按照如下图片配置。 
 

17.然后,选择System -> Auto-Assign Base Address,自动分配基地址。
 

18.选择System -> Auto-Assign IRQs,自动分配中断向量。
 
最后,得到如下结果:   
点击看大图 

19.点击Nios II More "cpu_NiosSmall" settings选项卡,进行处理器设定。Reset Address 设为onchip_ram_0,Exception Address 设为onchip_ram_0 .
 

20.点击System Generation选项卡,进行最后的设定并生成系统。
选中HDL.Generate system module logic in Verilog,如果需要仿真,也请选中Simulation.Create ModelSim(tm) project files.然后点击Generate,进行系统生成的任务。如下图:  
 
然后,就是漫长的等待,你可以忙里偷闲,喝一小杯咖啡。一般没有问题的话,可以看到系统提示:SUCCESS: SYSTEM GENERATION COMPLETED.如果看到此信息,恭喜恭喜,系统被正确生成了。如果失败,请返回并检查、修改!

第三节:初始化onchip_ram_0.hex。
接下来是初始化onchip_ram_0.hex,这样,系统一上电,就会开始跑流水灯,看着舒服一点啦。

1.点击Run Nios II IDE,启动Nios II IDE
 
2.选择File -> New -> Project,然后选择:Altera Nios II ---  C/C++ Application,然后选择Next
 
3.Name空栏中,您可以您可以依据需要,为其命名。比如,我为其取名为ezC6Be_StdF50_hello_led_1,完成后,选择Next。(注意,要在Select Project Template 中,选中Hello LED)  
点击看大图 
4.选中Create a new system library named: ......,最后选择Finish,系统会自动生成该项目。
点击看大图 
如下,是hello_led.c文件,一般情况下,无需作任何修改
点击看大图 
5.选择Project -> Build Project,编译整个项目。

常见问题:有的朋友常常会遇到如下错误:
点击看大图 
提示LED_PIO_BASE没有声明,这是因为名字不一致引起的比如,在生成SOPC系统时,双击PIO(Parallel I/O)(在Avalon Modules -> Other 下),为系统添加输出接口,你没有把该组件改名成LED_PIO,而是保留了原始的名字:PIO_0;但你又通过 IOWR_ALTERA_AVALON_PIO_DATA(LED_PIO_BASE, led);来向该组件写入数据,就会导致上述错误:解决方法:使两者名字一致。1。可以修改hello_led.c,通过 IOWR_ALTERA_AVALON_PIO_DATA(PIO_0_BASE, led) 通过来操作该PIO。2。或者可以修改sopc系统,为该PIO改名为LED_PIO。

系统分类: CPLD/FPGA  |  用户分类: FPGA  |  标签: 无标签  |  来源: 无分类  | 

点击查看原文

发表评论 阅读全文(129) | 回复(0)

发表于 2009/12/3 17:12:36

0

关于投票

nios II标准(Standard)系统的创建(1)

在此之前,我曾经过介绍过如何建立最小(small)的nios系统(见文章nios无痛入门)。在这儿,我将要介绍如何建立一个常用的标准(Standard)Nios系统。如果本文能对您有一点点帮助,我都会感到非常高兴。     

在本文中,我只挑要点讲一下,关于软件的详细使用指南,请您参考官方提供的help文档。我使用本站设计的ezNiosDK C6B开发板来示范这个实验;如果您采用自己的开发板,请您适当得修改,以适应您的开发板。

第一节:创建并初步配置项目。
1。创建项目。
创建一个空项目,我将他命名为ezC6Be_StdF50(请参考文章“nios无痛入门”,在此不再赘述),器件(Device)设置为EP1C6T144C8。
点击看大图 
 如果采用的是ezNiosDKC3系列,请选择EP1C3T144C8,如下图:
点击看大图 
2。执行如下script,主要目的是一次性映射PIN脚。
# Setup.tcl
# Setup pin setting

set_global_assignment -name RESERVE_ALL_UNUSED_PINS "AS INPUT TRI-STATED"
set_global_assignment -name ENABLE_INIT_DONE_OUTPUT ON
set_global_assignment -name CYCLONE_CONFIGURATION_DEVICE EPCS1

set_location_assignment PIN_16 -to OSC0

set_location_assignment PIN_125 -to RESET_
set_location_assignment PIN_28 -to LED\[0\]
set_location_assignment PIN_85 -to LED\[1\]
set_location_assignment PIN_96 -to LED\[2\]
set_location_assignment PIN_97 -to LED\[3\]

set_location_assignment PIN_27 -to KEY\[1\]
set_location_assignment PIN_17 -to KEY\[2\]
set_location_assignment PIN_92 -to KEY\[3\]
set_location_assignment PIN_93 -to KEY\[4\]

set_location_assignment PIN_51 -to SDRAM_CS_
set_location_assignment PIN_52 -to SDRAM_RAS_
set_location_assignment PIN_53 -to SDRAM_CAS_
set_location_assignment PIN_56 -to SDRAM_WE_

set_location_assignment PIN_39 -to SDRAM_CKE
set_location_assignment PIN_26 -to SDRAM_CLK

set_location_assignment PIN_50 -to SDRAM_BA\[0\]
set_location_assignment PIN_49 -to SDRAM_BA\[1\]

set_location_assignment PIN_47 -to SDRAM_A\[0\]
set_location_assignment PIN_42 -to SDRAM_A\[1\]
set_location_assignment PIN_41 -to SDRAM_A\[2\]
set_location_assignment PIN_40 -to SDRAM_A\[3\]
set_location_assignment PIN_34 -to SDRAM_A\[4\]
set_location_assignment PIN_33 -to SDRAM_A\[5\]
set_location_assignment PIN_32 -to SDRAM_A\[6\]
set_location_assignment PIN_31 -to SDRAM_A\[7\]
set_location_assignment PIN_35 -to SDRAM_A\[8\]
set_location_assignment PIN_36 -to SDRAM_A\[9\]
set_location_assignment PIN_48 -to SDRAM_A\[10\]
set_location_assignment PIN_37 -to SDRAM_A\[11\]
set_location_assignment PIN_38 -to SDRAM_A\[12\]

set_location_assignment PIN_69 -to SDRAM_DQ\[0\]
set_location_assignment PIN_68 -to SDRAM_DQ\[1\]
set_location_assignment PIN_67 -to SDRAM_DQ\[2\]
set_location_assignment PIN_62 -to SDRAM_DQ\[3\]
set_location_assignment PIN_61 -to SDRAM_DQ\[4\]
set_location_assignment PIN_60 -to SDRAM_DQ\[5\]
set_location_assignment PIN_59 -to SDRAM_DQ\[6\]
set_location_assignment PIN_58 -to SDRAM_DQ\[7\]
set_location_assignment PIN_71 -to SDRAM_DQ\[8\]
set_location_assignment PIN_72 -to SDRAM_DQ\[9\]
set_location_assignment PIN_73 -to SDRAM_DQ\[10\]
set_location_assignment PIN_74 -to SDRAM_DQ\[11\]
set_location_assignment PIN_78 -to SDRAM_DQ\[12\]
set_location_assignment PIN_77 -to SDRAM_DQ\[13\]
set_location_assignment PIN_76 -to SDRAM_DQ\[14\]
set_location_assignment PIN_75 -to SDRAM_DQ\[15\]

set_location_assignment PIN_57 -to SDRAM_DQM\[0\]
set_location_assignment PIN_70 -to SDRAM_DQM\[1\]

set_location_assignment PIN_99 -to FLASH_CE_
set_location_assignment PIN_100 -to FLASH_OE_
set_location_assignment PIN_128 -to FLASH_WE_

set_location_assignment PIN_98 -to EA\[1\]
set_location_assignment PIN_110 -to EA\[2\]
set_location_assignment PIN_111 -to EA\[3\]
set_location_assignment PIN_112 -to EA\[4\]
set_location_assignment PIN_113 -to EA\[5\]
set_location_assignment PIN_114 -to EA\[6\]
set_location_assignment PIN_119 -to EA\[7\]
set_location_assignment PIN_120 -to EA\[8\]
set_location_assignment PIN_131 -to EA\[9\]
set_location_assignment PIN_132 -to EA\[10\]
set_location_assignment PIN_133 -to EA\[11\]
set_location_assignment PIN_134 -to EA\[12\]
set_location_assignment PIN_139 -to EA\[13\]
set_location_assignment PIN_140 -to EA\[14\]
set_location_assignment PIN_141 -to EA\[15\]
set_location_assignment PIN_142 -to EA\[16\]
set_location_assignment PIN_11 -to EA\[17\]
set_location_assignment PIN_121 -to EA\[18\]
set_location_assignment PIN_122 -to EA\[19\]

set_location_assignment PIN_123 -to RYBY_

set_location_assignment PIN_130 -to EA\[20\]

set_location_assignment PIN_103 -to EDQ\[0\]
set_location_assignment PIN_105 -to EDQ\[1\]
set_location_assignment PIN_107 -to EDQ\[2\]
set_location_assignment PIN_109 -to EDQ\[3\]
set_location_assignment PIN_144 -to EDQ\[4\]
set_location_assignment PIN_3 -to EDQ\[5\]
set_location_assignment PIN_5 -to EDQ\[6\]
set_location_assignment PIN_7 -to EDQ\[7\]
set_location_assignment PIN_104 -to EDQ\[8\]
set_location_assignment PIN_106 -to EDQ\[9\]
set_location_assignment PIN_108 -to EDQ\[10\]
set_location_assignment PIN_143 -to EDQ\[11\]
set_location_assignment PIN_2 -to EDQ\[12\]
set_location_assignment PIN_4 -to EDQ\[13\]
set_location_assignment PIN_6 -to EDQ\[14\]
set_location_assignment PIN_10 -to EDQ\[15\]

set_location_assignment PIN_79 -to RXD1
set_location_assignment PIN_82 -to TXD1

set_location_assignment PIN_83 -to USBDN
set_location_assignment PIN_84 -to USBDP


第二节:创建NiosII系统。
1.选择Tools -> SOPC Builder,我将这个系统命名为sopc_ezC6Be_StdF50,就是在项目名前加上sopc_,您可以依据需要,为他命名。 

2。配置Component/Kit Library Search Path。
目的是在系统中增加本站设计的Flash编程器目录,请把光盘CD1上的/Example/ezNiosC6 拷贝到您的电脑的硬盘上。比如,我把他放在h:/DB2005/project/niosDK/CD/CD1/Example/中,然后在Altera SOPC Builder中,选择File -> SOPC Builder Setup,增加如下搜索路径:+h:/DB2005/project/niosDK/CD/CD1/Example/ezNiosC6

ezNiosC3 的用户如下操作:请把光盘CD1上的/Example/ezNiosC3 拷贝到您的电脑的硬盘上。比如,我把他放在h:/DB2005/project/niosDK/CD/CD1/Example/中,然后在Altera SOPC Builder中,选择File -> SOPC Builder Setup,增加如下搜索路径:+h:/DB2005/project/niosDK/CD/CD1/Example/ezNiosC3

并顺便检察Modelsim Directory是否正确:比如,我的是 g:/w2k/eda/fpga/altera/modeltech_6.0/win32

然后,你需要关闭Altera SOPC Builder,然后再重新通过QuartusII的Tools ->SOPC Builder来开启SOPC Builder,这样上述修改才能生效。  
 
3常见错误:有许多朋友往往在设置路径的时候,犯与下图类似的错误。错误在于第一个路径前面是不需要 + 号的!要去掉第一个路径前面的 + 号
 

3。Board Target 选择:ezC6_Programmer,clk选择 50.0 
点击看大图 
ezNiosC3的用户如下操作:Board Target 选择:ezC3_Programmer,clk选择 64.0
 

4。为系统添加Nios II处理器。
在Nios II core选项卡中,选择Nios II /e 。
点击看大图 
JTAG Debug Module选项卡中,选择Debug Level 1
 
Custom Instructions选项卡中空着即可。
 
最后选择Finish确认!    我把这个处理器改名(rename)为cpu_ezC6Be_StdF50,您可以依据需要,为其命名。

5.为系统添加onchip_ram。
双击左边的Memory -> On-Chip Memory,为系统添加2K byte onchip RAM,按照如下配置。我把它改名为onchip_ram_0,您可以依据需要,为其命名。
 

6。为系统添加DRAM控制器。

双击左边的Memory -> SDRAM Crontroller,为系统添加8M byte DRAM,请按照如下图片配置。
 
 

7。 为系统添加Tri-State Bridge。
双击左边的Bridge -> Avalon Tri-State Bridge,为系统添加Tri-State Bridge,请按照如下图片配置。  
 

8。为系统添加Flash接口。
双击左边的Memory -> Flash Memory(Common Flash Interface),为系统添加Flash,请按照如下图片配置。我把它改名(rename)为ext_flash,您可以依据需要,为其命名,但最好还是取名为ext_flash。ezNiosC3A,ezNiosC3B,ezNiosC6A的用户由于开发板上不带Flash,可以跳过此步。  
 
 

9。为系统添加EPCS Serial Flash Controller。
双击左边的Memory -> EPCS Serial Flash Controller,为系统添加EPCS Serial Flash Controller,请按照如下图片配置。ezNiosC3A,ezNiosC6A的用户由于开发板上不带该器件,可以跳过此步。

系统分类: CPLD/FPGA <