Adding gRPC as dependency via CMAKE fails - c++

I building a project that depends on gRPC. In the project I want to use gRPC, I'm using the following lines to find the package and add it as a dependency
# gRPC
find_package(gRPC CONFIG REQUIRED)
message(STATUS "Using gRPC ${gRPC_VERSION}")
#gRPC C++ plugin
find_program(gRPC_CPP_PLUGIN_EXECUTABLE grpc_cpp_plugin)
In the above snippet, cmake fails while executing find_package command and outputs the following error:
CMake Error at /usr/local/lib/cmake/grpc/gRPCConfig.cmake:15 (include):
include could not find load file:
/usr/local/lib/cmake/grpc/gRPCTargets.cmake
Call Stack (most recent call first):
src/CMakeLists.txt:15 (find_package)
I'm building the project inside a docker image where I've installed gRPC in the image, and the above error happens when trying to build the project that depends on it. This is how gRPC is installed in the Dockerfile (following the documentation)
RUN cd /tmp && git clone --recurse-submodules -b v1.46.3 --depth 1 --shallow-submodules https://github.com/grpc/grpc && \
cd grpc && git submodule update --init && \
mkdir build && cd build && \
cmake -DgRPC_INSTALL=ON -DgRPC_BUILD_TESTS=OFF -DCMAKE_INSTALL_PREFIX=/usr/local .. && \
make -j8 && \
make install && \
ldconfig && \
make clean && \
cd ../.. && \
rm -r grpc
Looking at the source code for gRPCConfig.cmake, it fails at the last line
(include(${CMAKE_CURRENT_LIST_DIR}/gRPCTargets.cmake)
It can't find the file gRPCTargets.cmake and the file doesn't exist in the grpc repo.
Has anyone faced a similar issue? How can I fix this?

Related

`uint_fast32_t` not found in namespace `boost` for boost > 1.74.0

I am trying to compile boost from sources but getting the error below.
It works fine for all versions of boost up to 1.74.0 but it breaks for anything newer than that.
Note that I am compiling a subset of boost modules, std::regex only.
Is there anything that changed on this version that makes these types unavailable?
clang-linux.compile.c++ bin.v2/libs/regex/build/clang-linux-14/release/link-static/visibility-hidden/posix_api.o
libs/regex/build/../src/posix_api.cpp:90:4: error: no type named 'uint_fast32_t' in namespace 'boost'; did you mean simply 'uint_fast32_t'?
boost::uint_fast32_t flags = (f & REG_PERLEX) ? 0 : ((f & REG_EXTENDED) ? regex::extended : regex::basic);
^~~~~~~~~~~~~~~~~~~~
uint_fast32_t
This script causes the error:
#!/bin/bash
set -exo pipefail
INSTALL_DIR=/ssd/tmp/install
TMPDIR=/ssd/tmp
TAG=boost-1.78.0
cd $TMPDIR
rm -rf boost
git clone https://github.com/boostorg/boost.git
cd boost
git checkout $TAG
allsm=" tools/build
tools/bcp
tools/boost_install
tools/boostdep
libs/regex
libs/config
libs/predef
libs/core
libs/detail
libs/headers
libs/integer"
for sm in $allsm; do
git submodule update --init $sm
done
#export LD=/usr/local/bin/ld.lld
#export CC='/usr/local/bin/clang'
#export CXX='/usr/local/bin/clang++'
#export CXXFLAGS='-O3 -stdlib=libc++ -std=c++20 -stdlib=libc++'
#export LDFLAGS="-lc++abi -lc++"
./bootstrap.sh
#--with-toolset=clang
./b2 headers
./b2 install -q -a \
--prefix=$INSTALL_DIR/local \
--build-type=minimal \
--layout=system \
--disable-icu \
--with-regex \
variant=release link=static runtime-link=static \
threading=single address-model=64 architecture=x86
# toolset=clang
However it works if you change the git tag from boost-1.78.0 to boost-1.71.0.
You aren't checking out all of the submodules, the simplest solution is to just follow the docs and run:
git clone --recursive https://github.com/boostorg/boost.git
or:
git clone git#github.com:boostorg/boost.git
git submodule update --init
After adding libs/throw_exception, and libs/assert to the submodules in your script it works for me on Ubuntu 20.04.
Here's the dockerfile I used for testing:
From ubuntu:20.04
RUN apt update
RUN apt-get install g++ git -y
RUN git clone https://github.com/boostorg/boost.git
RUN cd boost && git checkout boost-1.78.0
RUN cd boost && git submodule update --init tools/build
RUN cd boost && git submodule update --init tools/bcp
RUN cd boost && git submodule update --init tools/boost_install
RUN cd boost && git submodule update --init tools/boostdep
RUN cd boost && git submodule update --init libs/regex
RUN cd boost && git submodule update --init libs/config
RUN cd boost && git submodule update --init libs/predef
RUN cd boost && git submodule update --init libs/core
RUN cd boost && git submodule update --init libs/detail
RUN cd boost && git submodule update --init libs/headers
RUN cd boost && git submodule update --init libs/integer
RUN cd boost && git submodule update --init libs/assert
RUN cd boost && git submodule update --init libs/throw_exception
RUN cd boost && ./bootstrap.sh
RUN cd boost && ./b2 headers
RUN cd boost && ./b2 install -q -a \
--prefix=$INSTALL_DIR/local \
--build-type=minimal \
--layout=system \
--disable-icu \
--with-regex \
variant=release link=static runtime-link=static \
threading=single address-model=64 architecture=x86
Since Boost 1.76, Boost.Regex is a header-only library:
This is a header only library provided your compiler supports C++11 or later. Support for C++03 compilers is still present, but is now deprecated and may be removed without further notice!
The only people that still need to build the external libboost_regex library are those that are either:
Using the library in C++03 mode, or,
Using the deprecated POSIX C API's
Since you're compiling as C++11 or above, you should not need to build the libboost_regex library, so you can remove the --with-regex option.

Error executing a cmake project with Conan dependencies build via Clion's Docker integration

I'm trying to run a cmake project using conan as a package manager where the project is compiled in a docker container. I'm using Clion's docker integration support as outlined here.
CMakeLists.txt
cmake_minimum_required(VERSION 3.15)
project(FormatOutput CXX)
list(APPEND CMAKE_MODULE_PATH ${CMAKE_BINARY_DIR})
list(APPEND CMAKE_PREFIX_PATH ${CMAKE_BINARY_DIR})
add_definitions("-std=c++11")
if(NOT EXISTS "${CMAKE_BINARY_DIR}/conan.cmake")
message(STATUS "Downloading conan.cmake from https://github.com/conan-io/cmake-conan")
file(DOWNLOAD "https://raw.githubusercontent.com/conan-io/cmake-conan/0.18.1/conan.cmake"
"${CMAKE_BINARY_DIR}/conan.cmake"
TLS_VERIFY ON)
endif()
include(${CMAKE_BINARY_DIR}/conan.cmake)
conan_cmake_configure(REQUIRES fmt/9.1.0
GENERATORS cmake_find_package)
conan_cmake_autodetect(settings)
conan_cmake_install(PATH_OR_REFERENCE .
BUILD missing
REMOTE conancenter
SETTINGS ${settings})
find_package(fmt)
add_executable(main main.cpp)
target_link_libraries(main fmt::fmt)
Dockerfile
FROM debian:sid
RUN DEBIAN_FRONTEND="noninteractive" apt-get update && apt-get -y install tzdata
RUN apt-get update \
&& apt-get install -y build-essential \
gcc \
g++ \
gdb \
clang \
make \
ninja-build \
cmake \
autoconf \
automake \
libtool \
valgrind \
locales-all \
dos2unix \
rsync \
tar \
python3 \
python3-dev \
python3-pip \
&& apt-get clean
RUN pip install conan
ENV CONAN_USER_HOME=/.conan_docker
RUN mkdir $CONAN_USER_HOME && chmod 777 $CONAN_USER_HOME
docker-compose.yml
version: "3.4"
services:
clion-cpp-env:
image: clion/debian/cpp-env:1.0
build: .
platform: linux/amd64
cap_add:
- SYS_PTRACE
ports:
- 2222:22
volumes:
- "/tmp/conan_docker:/.conan_docker"
restart: on-failure
Clion Docker Toolchain Configuration
Build output
-- Conan: Using autogenerated Findfmt.cmake
-- Found fmt: 9.1.0 (found version "9.1.0")
-- Library fmtd found /.conan_docker/.conan/data/fmt/9.1.0/_/_/package/0d8b943d676dc202f180a2598d04457e173d7b97/lib/libfmtd.a
-- Found: /.conan_docker/.conan/data/fmt/9.1.0/_/_/package/0d8b943d676dc202f180a2598d04457e173d7b97/lib/libfmtd.a
-- Library fmtd found /.conan_docker/.conan/data/fmt/9.1.0/_/_/package/0d8b943d676dc202f180a2598d04457e173d7b97/lib/libfmtd.a
-- Found: /.conan_docker/.conan/data/fmt/9.1.0/_/_/package/0d8b943d676dc202f180a2598d04457e173d7b97/lib/libfmtd.a
-- Configuring done
-- Generating done
-- Build files have been written to: /tmp/docker_conan/cmake-build-debug-docker
[Finished]
Output on trying to run executable
====================[ Build | main | Debug-Docker ]=============================
/usr/bin/cmake --build /tmp/docker_conan/cmake-build-debug-docker --target main -j 6
ninja: error: '/.conan_docker/.conan/data/fmt/9.1.0/_/_/package/0d8b943d676dc202f180a2598d04457e173d7b97/lib/libfmtd.a', needed by 'main', missing and no known rule to make it
While the local compilation builds and runs without complaints, on compiling with the Docker toolchain on Clion, I'm able to build but not run the executable. Apparently the library is not found where conan installed it previously. How do I make this work?
Thanks to #Alan Birtles suggestion, the flaw in my approach was that the volumes/mount information was missing from my container instance.
Although I'd mentioned it in my docker-compose.yml file, it's likely that Clion is not running the docker container via docker-compose, and instead using the docker run command internally instead.
Thus, one needs to append to one's Docker Container Settings: the following volume mount information:
-v /path/to/localmachine/conan-docker:/conan_docker

What is a correct way to setup protobuf and grpc for cpp project?

I have a cpp project, and I want to build everything from source, to get latest things likned in. So under my project root I've created a 3rd_party folder and assemble following script:
sudo apt-get install autoconf automake libtool curl make g++ unzip -y
git clone https://github.com/google/protobuf.git
cd protobuf
git submodule update --init --recursive
./autogen.sh
./configure
make
make check
sudo make install
sudo ldconfig
cd ..
echo installing grpc
git clone --recurse-submodules -b v1.43.0 https://github.com/grpc/grpc
export MY_INSTALL_DIR=$HOME/.local
be sure that its exists
cd grpc
mkdir -p cmake/build
pushd cmake/build
cmake -DgRPC_INSTALL=ON -DgRPC_BUILD_TESTS=OFF -DCMAKE_INSTALL_PREFIX=$MY_INSTALL_DIR ../..
make -j
make install
popd
i've encountered following flaws:
grpc v1.43.0 clones 3rd party submodule protoc v3.18, which after build has problems - protoc binary says "cpp plugin not found", when trying to generate
To overcome that I've copied sources obtained in the first part of script, to 3rd party subfolder of second part, to gurantee it to be 3.19 - then after compilation protoc working great, plugins are in place, and grpc is linked against latest version.
Very weird issue, needs understanding why it clones outdated version, and why 3.18 has no plugins under same build parameters as 3.19
in cmakelists find_package(Protobuf REQUIRED) fails at all
find_package( gRPC REQUIRED ) is not operating properly:
Found package configuration file:
[cmake]
[cmake] /home/a/.local/lib/cmake/grpc/gRPCConfig.cmake
[cmake]
[cmake] but it set gRPC_FOUND to FALSE so package "gRPC" is considered to be NOT
[cmake] FOUND. Reason given by package:
[cmake]
[cmake] The following imported targets are referenced, but are missing:
[cmake] protobuf::libprotobuf protobuf::libprotoc
Question
How can I write script, that in an empty folder will get me everything, related to grpc 3rd party libs and tools, that I need for project?
Here are the steps I took:
$ mkdir .local
$ export INSTALL_PREFIX="$PWD/.local"
$ export CMAKE_GENERATOR=Ninja # optional, but recommended
$ git clone --recurse-submodules -b v3.19.3 --depth 1 https://github.com/google/protobuf.git
$ pushd protobuf
$ ./autogen.sh
$ ./configure --prefix=$INSTALL_PREFIX
$ make -j$(nproc)
$ make install
$ popd
$ git clone --recurse-submodules -b v1.43.0 --depth 1 https://github.com/grpc/grpc.git
$ cmake -S grpc -B .build/grpc \
-DCMAKE_BUILD_TYPE=Release \
-DCMAKE_INSTALL_PREFIX=$INSTALL_PREFIX \
-DCMAKE_PREFIX_PATH=$INSTALL_PREFIX \
-DgRPC_INSTALL=ON \
-DgRPC_BUILD_TESTS=OFF \
-DgRPC_PROTOBUF_PROVIDER=package \
-DABSL_PROPAGATE_CXX_STD=ON
$ cmake --build .build/grpc --target install
...
$ mkdir example
$ echo "int main () { return 0; }" > example/main.cpp
$ vim example/CMakeLists.txt
$ cat example/CMakeLists.txt
cmake_minimum_required(VERSION 3.22)
project(example)
find_package(gRPC REQUIRED)
add_executable(main main.cpp)
target_link_libraries(main PRIVATE gRPC::grpc++)
$ cmake -S example -B .build/example \
-DCMAKE_BUILD_TYPE=Release \
-DCMAKE_PREFIX_PATH=$INSTALL_PREFIX
$ cmake --build .build/example
...
I build protobuf separately because gRPC doesn't set up its dependencies in CMake correctly when using its internal protobuf build (I tried both ways). This involves passing --prefix to protobuf's ./configure script and passing -DgRPC_PROTOBUF_PROVIDER=package to gRPC's CMake build. The latter is a gRPC-specific variable that tells it not to build protobuf, but to search for it instead. I tell gRPC where to find protobuf by setting CMAKE_PREFIX_PATH, which is a standard variable.

grpc::grpc_cpp_plugin failed with status code 1 when installed grpc locally

I use gRPC with ros melodic in ubuntu 18.04. Since protobuf 3.0.0 was install if I got ros-melodic-desktop-full installed, I installed grpc in a custom path.
My CMakeLists.txt check if gRPC founded, if not it will install it in project scope using FetchContent.
When it get gRPC throught FetchContent, every thing goes fine. But when I export these two veriables
export gRPC_DIR=~/.grpc/
export Protobuf_DIR=~/.grpc/
in my .bashrc to let CMake find my gRPC and Protobuf installed locally. It will run into error when CMake execute the custom command compile the proto files.
Error Log:
grpc::grpc_cpp_plugin: program not found or is not executable
Please specify a program using absolute path or make sure the program is available in your PATH system variable
--grpc_out: protoc-gen-grpc: Plugin failed with status code 1.
And if I replace grpc::grpc_cpp_plugin with the absolute path of grpc_cpp_plugin, which is $HOME/.grpc/bin/grpc_cpp_plugin, it works fine.
Here is my install script:
#!/bin/bash
git clone --recurse-submodules -b v1.28.0 --depth 1 https://github.com/grpc/grpc
cd grpc
mkdir -p cmake/build
cd cmake/build
mkdir ~/.grpc
cmake -DCMAKE_BUILD_TYPE=Release \
-DgRPC_INSTALL=ON \
-DgRPC_PROTOBUF_PACKAGE_TYPE=CONFIG \
-DgRPC_BUILD_TESTS=OFF \
-DCMAKE_CXX_FLAGS=-latomic \
-DCMAKE_INSTALL_PREFIX=~/.grpc ../..
make -j$(nproc) && make install && make clean
Here is part of my CMakeLists.txt:
...
find_package(Protobuf CONFIG)
find_package(gRPC CONFIG)
if(NOT ${gRPC_FOUND})
include(cmake_module/FetchGRPC.cmake)
else()
set(_PROTOBUF_PROTOC protobuf::protoc)
set(_GRPC_CPP_PLUGIN_EXECUTABLE grpc::grpc_cpp_plugin)
endif()
add_custom_command(
OUTPUT "${ProtoSrc}" "${GrpcSrc}" "${ProtoHds}" "${GrpcHds}"
COMMAND ${_PROTOBUF_PROTOC}
ARGS --grpc_out "${ProtoPath}"
--cpp_out "${ProtoPath}"
-I "${ProtoPath}"
--plugin=protoc-gen-grpc="${_GRPC_CPP_PLUGIN_EXECUTABLE}"
"${ProtoFile}"
DEPENDS "${ProtoFile}"
)
...
the FetchGRPC.cmake mention above:
include(FetchContent)
FetchContent_Declare(
gRPC
GIT_REPOSITORY https://github.com/grpc/grpc
GIT_TAG v1.28.0
GIT_PROGRESS TRUE
USES_TERMINAL_DOWNLOAD TRUE
)
set(FETCHCONTENT_QUIET OFF)
FetchContent_MakeAvailable(gRPC)
if (CMAKE_CROSSCOMPILING)
find_program(_GRPC_CPP_PLUGIN_EXECUTABLE grpc_cpp_plugin)
else ()
set(_GRPC_CPP_PLUGIN_EXECUTABLE $<TARGET_FILE:grpc_cpp_plugin>)
endif ()
set(_REFLECTION grpc++_reflection)
set(_GRPC_GRPCPP_UNSECURE grpc++_unsecure)
set(_PROTOBUF_LIBPROTOBUF libprotobuf)
set(_PROTOBUF_PROTOC $<TARGET_FILE:protoc>)
set(_GRPC_GRPCPP grpc++)

How do we use packages installed from vcpkg?

I'm installing packages (aws-sdk, jsoncpp, ..) from vcpkg into my cmake project. But I'm having hard time trying to use them in my project, it's really difficult to figure out how to get cmake to find the installed packages, somehow I managed to add the target path for AWS-SDK, but I'm finding it difficult for other packages. So my question is, how do we get cmake to find packages installed using vcpkg?
Here is how my CMakeLists.txt file looks like:
cmake_minimum_required(VERSION 3.2)
set(CMAKE_CXX_STANDARD 11)
project(compiler LANGUAGES CXX)
include_directories(${JSONCPP_INCLUDE_DIRS})
find_package(AWSSDK REQUIRED COMPONENTS s3)
add_executable(${PROJECT_NAME} compiler.cpp)
target_link_libraries(${PROJECT_NAME} ${AWSSDK_LINK_LIBRARIES})
target_link_libraries(${PROJECT_NAME} ${JSONCPP_LINK_LIBRARIES})
And here is the docker file where I'm installing vcpkg and then these packages.
FROM ubuntu:18.04
WORKDIR /app
RUN apt-get update && \
apt-get install ffmpeg \
g++ \
git \
curl \
zip \
unzip \
tar \
openssl \
gcc \
cmake \
zlib1g-dev \
libcurl4-openssl-dev \
libssl-dev \
uuid-dev \
libpulse-dev \
make \
pkg-config -y
RUN git clone https://github.com/Microsoft/vcpkg.git && \
./vcpkg/bootstrap-vcpkg.sh
RUN ./vcpkg/vcpkg install "aws-sdk-cpp[s3]" --recurse
RUN ./vcpkg/vcpkg install "jsoncpp"
COPY . .
RUN DIR=compiler && mkdir ${DIR} && cd ${DIR} && \
cmake .. -DCMAKE_TOOLCHAIN_FILE=../vcpkg/scripts/buildsystems/vcpkg.cmake && \
cmake --build .
CMD cd compiler && ls -a && ./compiler