FPGA基础知识23(Verilog中条件编译命令_`ifdef、`else、`endif_用法)

来自:https://wenku.baidu.com/view/084ce39427d3240c8547ef2f.html

 

Verilog 中条件编译命令 `ifdef 、 `else 、 `endif 用法
一般情况下, Verilog HDL源程序中所有的行都参加编译。但是有时候希望
对其中的一部份内容只有在条件满足的时候才进行编译, 也就是对一部分内容指
定编译的条件, 这就是“条件编译”。

 

有时, 希望当满足条件时对一组语句进行
编译,当条件不满足时则对另外一组语句进行编译。

 


条件编译命令的几种形式:
( 1) ` ifdef 宏名(标识符)
程序段 1
`else
程序段 2
`endif
它的 作用是当宏名已经被定义过(此处需要采用 `define 命令定义),则对
程序段1进行编译, 程序段2将被忽略; 否则编译程序段2, 程序段1将被忽落。
其中 `else 部分可以没有,即:
(2) ` ifdef 宏名(标识符)
程序段1
`endif
这里的“宏名”是一个 Verilog HDL 的标识符, “程序段”可以是 Verilog
HDL语句组,也可以是命令行。这些命令可以出现在源程序的任何地方。
注意: 被忽略掉不进行编译的程序段部分也要符合 Verilog HDL程序的语言
规则。


通常在 Verilog HDL程序中用到 ` ifdef 、 `else 、 `endif 编译命令的情况有
以下几种:
(1)选择一个模板的不同代表部分。
(2)选择不同的时许或结构信息。
(3)对不同的EDA工具,选择不同的激励。


最常用的情况是: Verilog HDL 代码中的一部分可能适用于某个编译环境,
但不适用于另一个环境,如果设计者不想为两个环境创建两个不同版本的
Verilog 设计, 还有一种方法就是所谓的条件编译, 即设计者在代码中指定其中
某一部分只有在设置了特定的标志后, 这一段代码才能被编译, 即设计者在代码
中指定其中某一部分只有在设置了特定的标识后,这一段代码才能编译。


设计者也可能希望在程序的运行中,只有当设置了某个标志后,才能执行
Verilog 设计的某些部分,这就是所谓的条件执行。


条件编译可以用编译指令 ` ifdef 、 `else 、 `elsif 和`endif 实现。


` ifdef 和`ifndef 指令可以出现在设计的任何地方。 设计者可以有条件地编
译语句、 模块、 语句块、 声明和其他编译指令。

`else 指令时可选的。 一个`else
指令最多可以匹配一个 ` ifdef 或者`ifndef 。 一个 ` ifdef 或者`ifndef 可以匹配
任意数量的 `elsif 命令。 ` ifdef 或`ifndef 总是用相应的 `endif 来结束。

 


Verilog 文件中,条件编译标志可以用 `define 语句设置。如果没有设置条
件编译标志,那么 Verilog 编译器会简单地跳过该部分。 ` ifdef 语句中不允许
使用布尔表带式,例如使用 TEST && ADD_B2来表示编译条件是不允许的。

 


#ifdef #else #endif 的用法
预处理就是在进行编译的第一遍词法扫描和语法分析之前所作的工作。说白
了, 就是对源文件进行编译前, 先对预处理部分进行处理, 然后对处理后的代码
进行编译。这样做的好处是,经过处理后的代码,将会变的很精短。


关于预处理命令中的文件包含( #include ),宏定义( #define ),书上已
经有了详细的说明,在这里就不详述了。这里主要是对条件编译
( #ifdef,#else,#endif,#if 等)进行说明。以下分 3 种情况:


1:情况 1:
#ifdef _XXXX
... 程序段 1...
#else
... 程序段 2...
#endif
这表明如果标识符 _XXXX已被#define 命令定义过则对程序段 1 进行编译;
否则对程序段 2 进行编译。
例:
#define NUM
.............
.............
.............
#ifdef NUM
printf(" 之前 NUM有过定义啦! :) \n");
#else
printf(" 之前 NUM没有过定义! :( \n");
#endif
}
如果程序开头有 #define NUM 这行,即 NUM有定义,碰到下面 #ifdef NUM
的时候,当然执行第一个 printf 。否则第二个 printf 将被执行。
我认为,用这种,可以很方便的开启 / 关闭整个程序的某项特定功能。


2: 情况 2:
#ifndef _XXXX
... 程序段 1...
#else
... 程序段 2...
#endif
这里使用了 #ifndef ,表示的是 if not def 。当然是和 #ifdef 相反的状况
(如果没有定义了标识符 _XXXX,那么执行程序段 1,否则执行程序段 2)。例子
就不举了。


3:情况 3:
#if 常量
... 程序段 1...
#else
... 程序段 2...
#endif
这里表示,如果常量为真(非 0,随便什么数字,只要不是 0),就执行程
序段 1,否则执行程序段 2。
我认为,这种方法可以将测试代码加进来。当需要开启测试的时候,只要
将常量变 1 就好了。而不要测试的时候,只要将常量变 0。
我们主要使用以下几种方法 , 假设我们已在程序首部定义# ifdef DEBUG 与#
ifdef TEST :
1. 利用# ifdef/ # endif 将某程序功能模块包括进去, 以向某用户提供该功
能。
在程序首部定义# ifdef HNLD :
# ifdef HNLD
# include"n166_hn.c"
# endif
如果不许向别的用户提供该功能,则在编译之前将首部的 HNLD加一下划线
即可。
2. 在每一个子程序前加上标记,以便追踪程序的运行。
# ifdef DEBUG
printf(" Now is in hunan !");
# endif
3. 避开硬件的限制。 有时一些具体应用环境的硬件不一样, 但限于条件, 本
地缺乏这种设备,于是绕过硬件,直接写出预期结果。具体做法是 :
# ifndef TEST
i=dial();
// 程序调试运行时绕过此语句
# else
i=0;
# endif
调试通过后,再屏蔽 TEST的定义并重新编译,即可发给用户使用了。

你可能感兴趣的:(FPGA基础知识)