Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

NP-346 add updates to emsdk recipe and fix for nodejs recipe #14

Open
wants to merge 9 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 4 additions & 3 deletions .github/workflows/conan-package.yml
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ on:
branches:
- main
- 'CURA-*'
- 'NP-*'

permissions:
contents: read
Expand All @@ -30,7 +31,7 @@ jobs:
with:
PATTERNS: |
recipes/**/*.*

- name: Sync pip requirements
run: wget https://raw.githubusercontent.com/Ultimaker/cura-workflows/main/.github/workflows/requirements-runner.txt -O .github/workflows/requirements-runner.txt

Expand Down Expand Up @@ -73,9 +74,9 @@ jobs:
restore-keys: |
${{ runner.os }}-conan-downloads-

# TODO: Change to main once merged
# TODO: Change NP-346 to main once merged
- name: Export changed recipes
run: |
mkdir runner_scripts
wget https://raw.githubusercontent.com/Ultimaker/cura-workflows/main/runner_scripts/upload_conan_recipes.py -O runner_scripts/upload_conan_recipes.py
wget https://raw.githubusercontent.com/Ultimaker/cura-workflows/NP-346/runner_scripts/upload_conan_recipes.py -O runner_scripts/upload_conan_recipes.py
python runner_scripts/upload_conan_recipes.py --user ultimaker --branch ${{ github.ref_name }} --remote cura ${{ env.GIT_DIFF_FILTERED }}
88 changes: 88 additions & 0 deletions recipes/emsdk/all/conandata.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
sources:
"3.1.71":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.71.tar.gz"
sha256: "ea1bbd1974a3323710fc6e585aad20b056fed634df11db2ee3556bfd18e96afd"
"3.1.65":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.65.tar.gz"
sha256: "6000c66fc5ca81117cbf9f0fd72e288992915bc16df9e6d77c607fab05b472eb"
"3.1.50":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.50.tar.gz"
sha256: "7491a881eb5ee15fe81bbabcfff1fd571e45ccdb24a81890af429f9970cbd1f3"
"3.1.49":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.49.tar.gz"
sha256: "c99d98da9241c7e72784bc764a3e60a65d8f27202d45f3cd422b2ac7245380d9"
"3.1.48":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.48.tar.gz"
sha256: "94b965ba8f2ff0949ff67c6943bf5638a1b8850e4491a25413cdaff5b18da42b"
"3.1.47":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.47.tar.gz"
sha256: "a882560a83cbacec67867e7ce6b00420d557e71c501b523d2ed956ded021f9b4"
"3.1.46":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.46.tar.gz"
sha256: "5dd94e557b720800a60387ec078bf3b3a527cbd916ad74a696fe399f1544474f"
"3.1.45":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.45.tar.gz"
sha256: "8b5b3433eb732dcc7643a2707a12fd5cbe793a5dadbbae9a60c24a737a78fe33"
"3.1.44":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.44.tar.gz"
sha256: "cb8cded78f6953283429d724556e89211e51ac4d871fcf38e0b32405ee248e91"
"3.1.31":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.31.tar.gz"
sha256: "1d38b7375e12e85197165a4c51d76d90e1d9db8c2c593b64cfaec4338af54750"
"3.1.30":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.30.tar.gz"
sha256: "7b9c4e0b19f08df9f0d807112926f3908fe73a2960b752a87c3862956da8b9a8"
"3.1.29":
url: "https://github.com/emscripten-core/emsdk/archive/refs/tags/3.1.29.tar.gz"
sha256: "506376d0d2a71fc3dd1a4dba6fb4cf18f0a2fa4e1936aa04ba4b59f2d435bf3f"
"3.1.23":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.23.tar.gz"
sha256: "a2609fd97580e4e332acbf49b6cc363714982f06cb6970d54c9789df8e91381c"
"3.1.20":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.20.tar.gz"
sha256: "fd336c6d3e51c7205a8ec68e835c442dcbb187f92e50c42b3d7d54a312072ef7"
"3.1.18":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.18.tar.gz"
sha256: "6479c60710bfb1d146a8bdd8619b693699e73185c850a6eb79ef2bd7e2a8e411"
"3.1.17":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.17.tar.gz"
sha256: "f52359d3f265162dc875ac4c9d4570abc9d012e30bef8d380cb74f0e427800a3"
"3.1.16":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.16.tar.gz"
sha256: "0a7a822e09bb22d081a49bf4229377689aef473376f36b5fe62db040d7e1c065"
"3.1.15":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.15.tar.gz"
sha256: "74c7c54b3544555ec38d1e9dcc7e90b9f49ed0e04f2cc3fd44663c598af24124"
"3.1.12":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.12.tar.gz"
sha256: "1b8d8fdebf9f155131ba74f91d2c0dd572b2ba5d1d4a22fb123d20d3ca258e30"
"3.1.7":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.7.tar.gz"
sha256: "bcceced0b7cad2e08375adf74ef20fa431230abbae8766bdad268c43e34f8d03"
"3.1.5":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.5.tar.gz"
sha256: "ae540d681aa04f32b92afbda1c9ef737aa03c81222c1ce3fd567de5af7d36625"
"3.1.4":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.4.tar.gz"
sha256: "7dc13d967705582e11ff62ae143425dbc63c38372f1a1b14f0cb681fda413714"
"3.1.3":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.3.tar.gz"
sha256: "c03767ad4b6d24f143c0a4922735c80ec17d745191ebf54b8f97dbe5d81eb52f"
"3.1.0":
url: "https://github.com/emscripten-core/emsdk/archive/3.1.0.tar.gz"
sha256: "a2c5f3cf36525cf6a4b569f9d25500e3b2f7341c6e6779b54bcf4703b834202d"
"3.0.1":
url: "https://github.com/emscripten-core/emsdk/archive/3.0.1.tar.gz"
sha256: "3a51e17d45878a5c6d1b6c20f35d308b95d58d56dbfbee4ec058e2ee216b2c90"
"3.0.0":
url: "https://github.com/emscripten-core/emsdk/archive/3.0.0.tar.gz"
sha256: "a41dccfd15be9e85f923efaa0ac21943cbab77ec8d39e52f25eca1ec61a9ac9e"
"2.0.34":
url: "https://github.com/emscripten-core/emsdk/archive/2.0.34.tar.gz"
sha256: "a96ddf34de8de779c78be2785df04ae63c9a557da9e83e85332cda3d01bca250"
"2.0.31":
url: "https://github.com/emscripten-core/emsdk/archive/2.0.31.tar.gz"
sha256: "6bf70f4522308de1941200f8cdb9bde6967ba7aacb03445e9d136a5dd812b728"
"2.0.30":
url: https://github.com/emscripten-core/emsdk/archive/refs/tags/2.0.30.tar.gz
sha256: 69050d76c8907a58f99b08831e8cb7a4fba857efec6037d5e59df4b73111ba36
198 changes: 198 additions & 0 deletions recipes/emsdk/all/conanfile.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,198 @@
from conan import ConanFile, conan_version
from conan.tools.build import cross_building
from conan.tools.env import Environment
from conan.tools.files import chdir, copy, get, replace_in_file
from conan.tools.layout import basic_layout
from conan.tools.scm import Version
import json
import os


required_conan_version = ">=1.52.0"


class EmSDKConan(ConanFile):
name = "emsdk"
description = "Emscripten SDK. Emscripten is an Open Source LLVM to JavaScript compiler"
url = "https://github.com/conan-io/conan-center-index"
homepage = "https://github.com/kripken/emscripten"
topics = ("emsdk", "emscripten", "sdk")
license = "MIT"
settings = "os", "arch", "compiler", "build_type"

short_paths = True

@property
def _settings_build(self):
return getattr(self, "settings_build", self.settings)

def layout(self):
basic_layout(self, src_folder="src")

def build_requirements(self):
self.test_requires("nodejs/20.16.0")
# self.requires("python") # FIXME: Not available as Conan package
# self.requires("wasm") # FIXME: Not available as Conan package

def package_id(self):
del self.info.settings.compiler
del self.info.settings.build_type

def source(self):
get(self, **self.conan_data["sources"][self.version],
destination=self.source_folder, strip_root=True)

@property
def _relative_paths(self):
return ["bin", os.path.join("bin", "upstream", "emscripten")]

@property
def _paths(self):
return [os.path.join(self.package_folder, path) for path in self._relative_paths]

@property
def _emsdk(self):
return os.path.join(self.package_folder, "bin")

@property
def _emscripten(self):
return os.path.join(self.package_folder, "bin", "upstream", "emscripten")

@property
def _em_config(self):
return os.path.join(self.package_folder, "bin", ".emscripten")

@property
def _em_cache(self):
return os.path.join(self.package_folder, "bin", ".emscripten_cache")

def generate(self):
env = Environment()
env.prepend_path("PATH", self._paths)
env.define_path("EMSDK", self._emsdk)
env.define_path("EMSCRIPTEN", self._emscripten)
env.define_path("EM_CONFIG", self._em_config)
env.define_path("EM_CACHE", self._em_cache)
env.vars(self, scope="emsdk").save_script("emsdk_env_file")

@staticmethod
def _chmod_plus_x(filename):
if os.name == "posix":
os.chmod(filename, os.stat(filename).st_mode | 0o111)

def _tools_for_version(self):
ret = {}
# Select release-upstream from version (wasm-binaries)
with open(os.path.join(self.source_folder, "emscripten-releases-tags.json"), "r") as f:
data = json.load(f)
ret["wasm"] = f"releases-upstream-{data['releases'][self.version]}-64bit"
# Select python and node versions
with open(os.path.join(self.source_folder, "emsdk_manifest.json"), "r") as f:
data = json.load(f)
tools = data["tools"]
if self.settings.os == "Windows":
python = next((it for it in tools if (it["id"] == "python" and not it.get("is_old", False))), None)
ret["python"] = f"python-{python['version']}-64bit"
node = next((it for it in tools if (it["id"] == "node" and not it.get("is_old", False))), None)
ret["nodejs"] = f"node-{node['version']}-64bit"
return ret

def build(self):
with chdir(self, self.source_folder):
emsdk = "emsdk.bat" if self._settings_build.os == "Windows" else "./emsdk"
self._chmod_plus_x("emsdk")

# Install required tools
required_tools = self._tools_for_version()
for key, value in required_tools.items():
if key != 'nodejs':
self.run(f"{emsdk} install {value}")
self.run(f"{emsdk} activate {value}")

def package(self):
copy(self, "LICENSE", src=self.source_folder, dst=os.path.join(self.package_folder, "licenses"))
copy(self, "*", src=self.source_folder, dst=os.path.join(self.package_folder, "bin"))
emscripten = os.path.join(self.package_folder, "bin", "upstream", "emscripten")
toolchain = os.path.join(emscripten, "cmake", "Modules", "Platform", "Emscripten.cmake")
# FIXME: conan should add the root of conan package requirements to CMAKE_PREFIX_PATH (LIBRARY/INCLUDE -> ONLY; PROGRAM -> NEVER)
# allow to find conan libraries
replace_in_file(self, toolchain,
"set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY)",
"set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY BOTH)")
replace_in_file(self, toolchain,
"set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY)",
"set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE BOTH)")
replace_in_file(self, toolchain,
"set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)",
"set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE BOTH)")
if not cross_building(self):
self.run("embuilder build MINIMAL", env=["conanemsdk", "conanrun"]) # force cache population
# the line below forces emscripten to accept the cache as-is, even after re-location
# https://github.com/emscripten-core/emscripten/issues/15053#issuecomment-920950710
os.remove(os.path.join(self._em_cache, "sanity.txt"))
self.run("npm install", cwd=emscripten, env=["conanemsdk", "conanrun", "conanbuild"])

def _define_tool_var(self, value):
suffix = ".bat" if self.settings.os == "Windows" else ""
path = os.path.join(self._emscripten, f"{value}{suffix}")
self._chmod_plus_x(path)
return path

def package_info(self):
self.cpp_info.bindirs = self._relative_paths
self.cpp_info.includedirs = []
self.cpp_info.libdirs = []
self.cpp_info.resdirs = []

# If we are not building for Emscripten, probably we don't want to inject following environment variables,
# but it might be legit use cases... until we find them, let's be conservative.
if not hasattr(self, "settings_target") or self.settings_target is None:
return

if self.settings_target.os != "Emscripten":
self.output.warning(f"You've added {self.name}/{self.version} as a build requirement, while os={self.settings_target.os} != Emscripten")
return

toolchain = os.path.join(self.package_folder, "bin", "upstream", "emscripten", "cmake", "Modules", "Platform", "Emscripten.cmake")
self.conf_info.prepend("tools.cmake.cmaketoolchain:user_toolchain", toolchain)

self.buildenv_info.define_path("EMSDK", self._emsdk)
self.buildenv_info.define_path("EMSCRIPTEN", self._emscripten)
self.buildenv_info.define_path("EM_CONFIG", self._em_config)
self.buildenv_info.define_path("EM_CACHE", self._em_cache)

compiler_executables = {
"c": self._define_tool_var("emcc"),
"cpp": self._define_tool_var("em++"),
}
self.conf_info.update("tools.build:compiler_executables", compiler_executables)
self.buildenv_info.define_path("CC", compiler_executables["c"])
self.buildenv_info.define_path("CXX", compiler_executables["cpp"])
self.buildenv_info.define_path("AR", self._define_tool_var("emar"))
self.buildenv_info.define_path("NM", self._define_tool_var("emnm"))
self.buildenv_info.define_path("RANLIB", self._define_tool_var("emranlib"))
self.buildenv_info.define_path("STRIP", self._define_tool_var("emstrip"))

self.cpp_info.builddirs = [
os.path.join("bin", "releases", "src"),
os.path.join("bin", "upstream", "emscripten", "cmake", "Modules"),
os.path.join("bin", "upstream", "emscripten", "cmake", "Modules", "Platform"),
os.path.join("bin", "upstream", "emscripten", "system", "lib", "libunwind", "cmake", "Modules"),
os.path.join("bin", "upstream", "emscripten", "system", "lib", "libunwind", "cmake"),
os.path.join("bin", "upstream", "emscripten", "tests", "cmake", "target_library"),
os.path.join("bin", "upstream", "lib", "cmake", "llvm"),
]

if Version(conan_version).major < 2:
self.env_info.PATH.extend(self._paths)
self.env_info.CONAN_CMAKE_TOOLCHAIN_FILE = toolchain
self.env_info.EMSDK = self._emsdk
self.env_info.EMSCRIPTEN = self._emscripten
self.env_info.EM_CONFIG = self._em_config
self.env_info.EM_CACHE = self._em_cache
self.env_info.CC = compiler_executables["c"]
self.env_info.CXX = compiler_executables["cpp"]
self.env_info.AR = self._define_tool_var("emar")
self.env_info.NM = self._define_tool_var("emnm")
self.env_info.RANLIB = self._define_tool_var("emranlib")
self.env_info.STRIP = self._define_tool_var("emstrip")
4 changes: 4 additions & 0 deletions recipes/emsdk/all/test_package/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
cmake_minimum_required(VERSION 3.1)
project(test_package LANGUAGES CXX)

add_executable(${PROJECT_NAME} test_package.cpp)
40 changes: 40 additions & 0 deletions recipes/emsdk/all/test_package/conanfile.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
from conan import ConanFile
from conan.tools.env import Environment
from conan.tools.cmake import CMake, cmake_layout
import os


class TestPackageConan(ConanFile):
settings = "os", "arch", "compiler", "build_type"
generators = "CMakeToolchain", "VirtualBuildEnv"
test_type = "explicit"

def build_requirements(self):
self.tool_requires(self.tested_reference_str)

def layout(self):
cmake_layout(self)

def generate(self):
if self.settings.os == "Emscripten":
env = Environment()
env.define_path("EM_CACHE", os.path.join(self.build_folder, ".emcache"))
envvars = env.vars(self, scope="build")
envvars.save_script("em_cache")

def build(self):
# It only makes sense to build a library, if the target os is Emscripten
if self.settings.os == "Emscripten":
cmake = CMake(self)
cmake.configure()
cmake.build()

def test(self):
# Check the package provides working binaries
self.run("emcc -v")
self.run("em++ -v")

# Run the project that was built using emsdk
if self.settings.os == "Emscripten":
test_file = os.path.join(self.cpp.build.bindirs[0], "test_package.js")
self.run(f"node {test_file}")
8 changes: 8 additions & 0 deletions recipes/emsdk/all/test_package/test_package.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
#include <cstdlib>
#include <iostream>

int main()
{
std::cout << "conan-center-index\n";
return EXIT_SUCCESS;
}
7 changes: 7 additions & 0 deletions recipes/emsdk/all/test_v1_package/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
cmake_minimum_required(VERSION 3.1)
project(test_package LANGUAGES CXX)

include(${CMAKE_BINARY_DIR}/conanbuildinfo.cmake)
conan_basic_setup(TARGETS)

add_executable(${PROJECT_NAME} ../test_package/test_package.cpp)
Loading
Loading