I am trying to build Boost from source using emscripten.
One executable CMake project I have has a dependency on the following boost libraries:
So I am building the requested boost libraries using the following commands:
git clone --recursive https://github.com/boostorg/boost.git --branch boost-1.85.0
cd boost
./bootstrap.sh
./b2 --show-libraries
<Here, I see graph is indeed listed, so are filesystem and program_options>
./b2 toolset=emscripten link=static variant=release threading=multi runtime-link=static filesystem program_options graph
This last command exits with the following error:
don't know how to make <e>graph
...found 1 target...
...can't find 1 target...
If I omit graph
from the build, boost builds fine. Why can't I just build graph just like I can build filesystem, system and other libraries?
I'm using Ubuntu 22.04 from within a WSL environment, not sure if that matters.
So, I wanted to try this out. On my nix-setup I made an empty directory emscripten_projects
with default.nix
:
{pkgs ? import <nixpkgs> {}}:
pkgs.mkShell {
name = "emscripten boost shell";
nativeBuildInputs = with pkgs; [
pkg-config
cmake
emscripten
];
env = {
EM_CACHE = "/home/sehe/.emscripten_cache";
Boost_DIR = "/home/sehe/custom/emscripten_projects/emboost/stage/lib/cmake";
};
shellHook = ''
echo "Setting up emscripten cache in $EM_CACHE"
rsync -hxDa "${pkgs.emscripten}/share/emscripten/cache/" "$EM_CACHE"
chmod u+rwX -R "$EM_CACHE"
'';
}
This tiny shell definition installs cmake and emscripten. The most of the work is to avoid permission errors on the emscripten cache (see here).
Next up, I built stuff like this:
git clone --recursive https://github.com/boostorg/boost.git --branch boost-1.85.0 --depth=1 emboost --jobs=16
cd emboost
./bootstrap.sh
./b2 toolset=emscripten --with-graph
This all builds like clockwork: (fullres mp4 here, 69MiB)
Let's compile a demo, main.cpp
:
#include <boost/graph/adjacency_list.hpp>
#include <boost/graph/graph_utility.hpp>
#include <boost/graph/graphviz.hpp>
struct Vertex {
int id;
};
using G = boost::adjacency_list<boost::vecS, boost::vecS, boost::directedS, Vertex>;
int main() {
G g;
boost::dynamic_properties dp;
dp.property("node_id", get(&Vertex::id, g));
std::istringstream dot(R"(digraph G {
0;
1;
2;
0 -> 1;
1 -> 2;
2 -> 0;
})");
read_graphviz(dot, g, dp);
print_graph(g, get(&Vertex::id, g));
}
This specifically uses the linked-library feature read_graphviz
because it is NOT header-only: