FindFLEX

查找快速词法分析器 (Flex) 可执行文件,并提供一个宏来生成自定义构建规则。

该模块定义了以下变量

FLEX_FOUND

如果找到 flex 可执行文件,则为 True。

FLEX_EXECUTABLE

指向 flex 可执行文件的路径。

FLEX_VERSION

flex 的版本。

FLEX_LIBRARIES

flex 库。

FLEX_INCLUDE_DIRS

指向 flex 头文件的路径。

可以使用标准的 CMake 语法指定 flex 的最低要求版本,例如 find_package(FLEX 2.5.13)

如果在系统上找到 flex,该模块定义了宏

flex_target
flex_target(<Name> <FlexInput> <FlexOutput>
            [OPTIONS <options>...]
            [COMPILE_FLAGS <string>]
            [DEFINES_FILE <string>]
            )

它创建一个自定义命令,用于从 <FlexInput> 文件生成 <FlexOutput> 文件。<Name> 是一个别名,用于获取此自定义命令的详细信息。

选项包括

OPTIONS <options>...

在版本 4.0 中添加。

添加到 flex 命令行中的 flex 选项的 分号分隔列表

COMPILE_FLAGS <string>

自版本 4.0 起已弃用。

添加到 flex 命令行中的空格分隔的 flex 选项。 ;-列表 将不起作用。此选项已被弃用,建议使用 OPTIONS <options>...

DEFINES_FILE <string>

在版本 3.5 中添加。

如果 flex 配置为输出头文件,则可以使用此选项来指定其名称。

在版本 3.17 中更改:CMP0098 设置为 NEW 时,flexCMAKE_CURRENT_BINARY_DIR 目录中运行。

该宏定义了以下变量

FLEX_<Name>_DEFINED

如果宏成功运行,则为 True。

FLEX_<Name>_OUTPUTS

由自定义规则生成的源文件,是 <FlexOutput> 的别名。

FLEX_<Name>_INPUT

flex 源文件,是 <FlexInput> 的别名。

FLEX_<Name>_OUTPUT_HEADER

头文件 flex 输出(如果有)。

FLEX_<Name>_OPTIONS

在版本 4.0 中添加。

flex 命令行中使用的选项。

Flex 扫描器通常使用 Bison 定义的标记:Flex 生成的代码取决于 Bison 生成的头文件。此模块还定义了一个宏

add_flex_bison_dependency
add_flex_bison_dependency(<FlexTarget> <BisonTarget>)

它在扫描器和解析器之间添加所需的依赖关系,其中 <FlexTarget><BisonTarget> 分别是 flex_targetbison_target 宏的第一个参数。

示例

find_package(BISON)
find_package(FLEX)

bison_target(MyParser parser.y ${CMAKE_CURRENT_BINARY_DIR}/parser.cpp)
flex_target(MyScanner lexer.l  ${CMAKE_CURRENT_BINARY_DIR}/lexer.cpp)
add_flex_bison_dependency(MyScanner MyParser)

include_directories(${CMAKE_CURRENT_BINARY_DIR})
add_executable(Foo
  Foo.cc
  ${BISON_MyParser_OUTPUTS}
  ${FLEX_MyScanner_OUTPUTS}
)
target_link_libraries(Foo ${FLEX_LIBRARIES})

可以将其他命令行选项作为列表传递给 flex 可执行文件。例如,添加 --warn 选项以报告警告,以及 --noline (-L) 以不生成 #line 指令。

find_package(FLEX)

if(FLEX_FOUND)
  flex_target(MyScanner lexer.l lexer.cpp OPTIONS --warn --noline)
endif()

生成器表达式可以在 OPTIONS <options... 中使用。例如,仅为 Debug 构建类型添加 --debug (-d) 选项

find_package(FLEX)

if(FLEX_FOUND)
  flex_target(MyScanner lexer.l lexer.cpp OPTIONS $<$<CONFIG:Debug>:--debug>)
endif()