I'm working on an hobby project in C++, using flex
and bison
. I'm using CMake as my build system, and I had struggle in making all work together.
I'm quite new to CMake so the documentation seems quite minimal to me. It is showed how to link everything in one executable. But I'm trying to keep all the parts of my code separated, so I would like to have my flex
/ bison
file in a subfolder. My structure is this:
.
├── build
| └-- ...
├── CMakeLists.txt
├── flexbison
│ ├── CMakeLists.txt
│ ├── lexer.ll
│ └── parser.yy
├── lib
│ ├── CMakeLists.txt
│ └── ...
├── main.cpp
└── run.sh
So I want to have my yyparse
function separate from my main.cpp
, as well as my other C++ files. I managed to get it done in this way:
project_root/CMakeLists.txt
: cmake_minimum_required(VERSION 3.10)
# set the project name
project(progetto-di-prova VERSION 0.1)
add_subdirectory(flexbison)
add_executable(executable main.cpp)
target_include_directories(executable PUBLIC
"${PROJECT_BINARY_DIR}"
"${PROJECT_BINARY_DIR}/flexbison"
)
set_target_properties(executable PROPERTIES CXX_STANDARD 11)
target_link_libraries(executable parserlib)
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
flexbison/CMakeLists.txt
: find_package(FLEX)
find_package(BISON)
flex_target(lexer lexer.ll "${CMAKE_CURRENT_BINARY_DIR}/lexer.cpp")
bison_target(parser parser.yy ${CMAKE_CURRENT_BINARY_DIR}/parser.cpp
DEFINES_FILE ${CMAKE_CURRENT_BINARY_DIR}/parser.h)
add_flex_bison_dependency(lexer parser)
add_library(parserlib STATIC
${FLEX_lexer_OUTPUTS}
${BISON_parser_OUTPUTS}
)
main.cpp
file: #include <parser.h> // <-this was the line causing troule
#include <iostream>
extern int yylex(void);
int main(int argc, char *argv[])
{
yyparse();
return 0;
}
Now, the point is: is this the correct way of doing so ? Is it better to put the main
function in the bison
code?
My main problem, as highlighted in the code, was to include the parser.h
header file in the main.cpp
. Is this the CMake-way to do it ?
Thanks in advance!
If I were you I would have:
flexbison/CMakeLists.txt
:
...
add_library(parserlib STATIC
${FLEX_lexer_OUTPUTS}
${BISON_parser_OUTPUTS}
)
target_include_directories(parserlib PUBLIC
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}>
$<BUILD_INTERFACE:${CMAKE_CURRENT_BINARY_DIR}>
$<INSTALL_INTERFACE:include/parserlib> # <prefix>/include/parserlib
)
note: $<INSTALL_INTERFACE:include/parserlib>
need to be adapted if you want and how you install parserlib...
project_root/CMakeLists.txt
:
...
target_include_directories(executable PUBLIC
$<BUILD_INTERFACE:${CMAKE_CURRENT_BINARY_DIR}>)
...
Since executable
is "target_link" against parserlib
which provides public include directories, you don't need to list these directories anymore in executable
's include dirs.
ref: https://cmake.org/cmake/help/latest/command/target_include_directories.html
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.