Skip to content

Commit

Permalink
Merge pull request #1261 from emanuele-f/cryptography-42-and-rust
Browse files Browse the repository at this point in the history
Cryptography 42 and rust
  • Loading branch information
mhsmith authored Oct 17, 2024
2 parents e57c25f + d900438 commit 13c1fce
Show file tree
Hide file tree
Showing 8 changed files with 66 additions and 57 deletions.
1 change: 1 addition & 0 deletions server/pypi/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,7 @@ these can be installed using your distribution. Some of them have special entrie
[here](https://github.com/mzakharo/android-gfortran/releases/tag/r21e). Create a
`fortran` subdirectory in the same directory as this README, and unpack the .bz2 files
into it.
* `rust`: `rustup` must be on the PATH.


## Building a package
Expand Down
29 changes: 27 additions & 2 deletions server/pypi/build-wheel.py
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,7 @@ def main(self):
normalize_version(self.version))

self.non_python_build_reqs = set()
for name in ["cmake", "fortran"]:
for name in ["cmake", "fortran", "rust"]:
try:
self.meta["requirements"]["build"].remove(name)
except ValueError:
Expand Down Expand Up @@ -611,6 +611,10 @@ def get_common_env_vars(self, env):
env["CPPFLAGS"] = ""
env["LDSHARED"] = f"{env['CC']} -shared"

if exists(f"{self.host_env}/chaquopy/lib/libssl.so"):
# `cryptography` requires this variable.
env["OPENSSL_DIR"] = f"{self.host_env}/chaquopy"

def get_python_env_vars(self, env, pypi_env):
# Adding host_env to PYTHONPATH allows setup.py to import requirements, for
# example to call numpy.get_include().
Expand All @@ -633,7 +637,26 @@ def get_python_env_vars(self, env, pypi_env):

# Overrides sysconfig.get_platform and distutils.util.get_platform.
# TODO: consider replacing this with crossenv.
env["_PYTHON_HOST_PLATFORM"] = f"linux_{ABIS[self.abi].uname_machine}"
env["_PYTHON_HOST_PLATFORM"] = f"linux-{ABIS[self.abi].uname_machine}"

def get_rust_env_vars(self, env):
tool_prefix = ABIS[self.abi].tool_prefix
run(f"rustup target add {tool_prefix}")
env.update({
"RUSTFLAGS": f"-C linker={env['CC']} -L native={self.host_env}/chaquopy/lib",
"CARGO_BUILD_TARGET": tool_prefix,

# Normally PyO3 requires sysconfig modules, which are not currently
# available in the `target` packages for Python 3.12 and older. However,
# since PyO3 0.16.4, it's possible to compile abi3 modules without sysconfig
# modules. This only requires packages to specify the minimum python
# compatibility version via one of the "abi3-py*" features (e.g.
# abi3-py310). Doing this requires the "-L native" flag in RUSTFLAGS above.
# https://pyo3.rs/main/building-and-distribution#building-abi3-extensions-without-a-python-interpreter
"PYO3_NO_PYTHON": "1",
"PYO3_CROSS": "1",
"PYO3_CROSS_PYTHON_VERSION": self.python,
})

@contextmanager
def env_vars(self):
Expand All @@ -649,6 +672,8 @@ def env_vars(self):

if self.needs_python:
self.get_python_env_vars(env, pypi_env)
if "rust" in self.non_python_build_reqs:
self.get_rust_env_vars(env)

env.update({
# TODO: make everything use HOST instead, and remove this.
Expand Down
6 changes: 5 additions & 1 deletion server/pypi/compiler-wrapper.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,11 @@
valid_dirs = [abspath(f"{dirname(sys.argv[0])}/../..")]

def is_valid(dir, prefix):
if any(commonpath([vd, abspath(dir)]) == vd for vd in valid_dirs):
absdir = abspath(dir)
if (
any(commonpath([vd, absdir]) == vd for vd in valid_dirs)
or (".cargo" in absdir) or (".rustup" in absdir)
):
return True
else:
print(f"Chaquopy: ignored invalid {prefix} directory: {dir!r}", file=sys.stderr)
Expand Down
2 changes: 1 addition & 1 deletion server/pypi/packages/cffi/meta.yaml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
package:
name: cffi
version: "1.16.0"
version: "1.17.1"

build:
number: 0
Expand Down
22 changes: 0 additions & 22 deletions server/pypi/packages/cryptography/build-with-static-openssl.sh

This file was deleted.

33 changes: 2 additions & 31 deletions server/pypi/packages/cryptography/meta.yaml
Original file line number Diff line number Diff line change
@@ -1,38 +1,9 @@
package:
name: cryptography
version: "3.4.8"

build:
number: 2
script_env:
- CRYPTOGRAPHY_DONT_BUILD_RUST=1
version: "42.0.8"

requirements:
build:
- cffi 1.15.1
- setuptools-rust 0.11.6
- rust
host:
# This version of cryptography isn't compatible with OpenSSL 3. So to build it for
# Python 3.9 and 3.10, we link it against OpenSSL 1.1.
#
# We don't do this by supplying an OpenSSL 1.1 wheel with a shared library, because
# the Chaquopy runtime (perhaps unnecessarily) loads non-Python libraries using
# RTLD_GLOBAL, which could cause conflicts with the OpenSSL 3 library which Chaquopy
# loads on startup.
#
# Instead, we link against OpenSSL 1.1 statically, as follows:
# * Download an OpenSSL 1.1 build from
# https://github.com/beeware/cpython-android-source-deps/releases.
# * For each combination of Python version and ABI, run build-with-static-openssl.sh
# in this directory.
#
# Although this may cause some of OpenSSL's symbols to be exported by crytography's
# Python modules, that's safe because Python modules are loaded using RTLD_LOCAL. And
# although the GLOBAL/LOCAL distinction is only respected from API level 23, older
# versions wouldn't include earlier libraries in the symbol search order for later
# libraries anyway, unless they were listed in DT_NEEDED.
#
# More information:
# * https://github.com/aosp-mirror/platform_bionic/blob/master/android-changes-for-ndk-developers.md
# * https://github.com/android/ndk/issues/1244
- openssl
16 changes: 16 additions & 0 deletions server/pypi/packages/cryptography/patches/openssl_no_legacy.patch
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
--- src-original/src/rust/src/lib.rs
+++ src/src/rust/src/lib.rs
@@ -45,9 +45,10 @@
// serialization), RC4, Blowfish, IDEA, SEED, etc. These things
// are ugly legacy, but we aren't going to get rid of them
// any time soon.
- let load_legacy = env::var("CRYPTOGRAPHY_OPENSSL_NO_LEGACY")
- .map(|v| v.is_empty() || v == "0")
- .unwrap_or(true);
+
+ // Chaquopy: the legacy provider is not available.
+ let load_legacy = false;
+
let legacy = if load_legacy {
let legacy_result = provider::Provider::load(None, "legacy");
_legacy_provider_error(legacy_result.is_ok())?;
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
--- src-original/src/rust/Cargo.toml
+++ src/src/rust/Cargo.toml
@@ -10,7 +10,10 @@
[dependencies]
once_cell = "1"
cfg-if = "1"
-pyo3 = { version = "0.20", features = ["abi3"] }
+
+# Chaquopy: added abi3-py10 - see needs_rust in build-wheel.py.
+pyo3 = { version = "0.20", features = ["abi3", "abi3-py310"] }
+
asn1 = { version = "0.15.5", default-features = false }
cryptography-cffi = { path = "cryptography-cffi" }
cryptography-key-parsing = { path = "cryptography-key-parsing" }

0 comments on commit 13c1fce

Please sign in to comment.