Skip to content

Commit 7a0c31d

Browse files
committed
unix: add support for s390x Linux cross builds
This was trivial to get working since Debian has a cross toolchain for it.
1 parent bbc930c commit 7a0c31d

File tree

9 files changed

+106
-3
lines changed

9 files changed

+106
-3
lines changed

.github/workflows/linux.yml

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -128,6 +128,7 @@ jobs:
128128
- 'i686-unknown-linux-gnu'
129129
- 'mips-unknown-linux-gnu'
130130
- 'mipsel-unknown-linux-gnu'
131+
- 's390x-unknown-linux-gnu'
131132
- 'x86_64-unknown-linux-gnu'
132133
- 'x86_64-unknown-linux-musl'
133134
py:
@@ -162,6 +163,10 @@ jobs:
162163
py: 'cpython-3.8'
163164
- triple: 'mipsel-unknown-linux-gnu'
164165
py: 'cpython-3.10'
166+
- triple: 's390x-unknown-linux-gnu'
167+
py: 'cpython-3.8'
168+
- triple: 's390x-unknown-linux-gnu'
169+
py: 'cpython-3.10'
165170
# We don't publish noopt builds for GNU Linux when PGO is available.
166171
- triple: 'i686-unknown-linux-gnu'
167172
optimizations: 'noopt'
@@ -193,6 +198,10 @@ jobs:
193198
optimizations: 'pgo'
194199
- triple: 'mipsel-unknown-linux-gnu'
195200
optimizations: 'pgo+lto'
201+
- triple: 's390x-unknown-linux-gnu'
202+
optimizations: 'pgo'
203+
- triple: 's390x-unknown-linux-gnu'
204+
optimizations: 'pgo+lto'
196205

197206
needs:
198207
- pythonbuild

cpython-unix/build-cpython.sh

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -622,6 +622,11 @@ if [ "${BUILD_TRIPLE}" != "${TARGET_TRIPLE}" ]; then
622622
CONFIGURE_FLAGS="${CONFIGURE_FLAGS} ac_cv_file__dev_ptc=no"
623623
CONFIGURE_FLAGS="${CONFIGURE_FLAGS} ac_cv_file__dev_ptmx=no"
624624
;;
625+
s390x-unknown-linux-gnu)
626+
CONFIGURE_FLAGS="${CONFIGURE_FLAGS} ac_cv_buggy_getaddrinfo=no"
627+
CONFIGURE_FLAGS="${CONFIGURE_FLAGS} ac_cv_file__dev_ptc=no"
628+
CONFIGURE_FLAGS="${CONFIGURE_FLAGS} ac_cv_file__dev_ptmx=no"
629+
;;
625630
x86_64-unknown-linux-musl)
626631
;;
627632
*)

cpython-unix/build-libX11.sh

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,9 @@ if [ "${BUILD_TRIPLE}" != "${TARGET_TRIPLE}" ]; then
6666
mips64el-unknown-linux-gnuabi64)
6767
EXTRA_FLAGS="${EXTRA_FLAGS} --enable-malloc0returnsnull"
6868
;;
69+
s390x-unknown-linux-gnu)
70+
EXTRA_FLAGS="${EXTRA_FLAGS} --enable-malloc0returnsnull"
71+
;;
6972
*)
7073
echo "cross-compiling but malloc(0) override not set; failures possible"
7174
;;
@@ -91,6 +94,9 @@ case "${TARGET_TRIPLE}" in
9194
mips64el-unknown-linux-gnuabi64)
9295
CC_FOR_BUILD=gcc
9396
;;
97+
s390x-unknown-linux-gnu)
98+
CC_FOR_BUILD=gcc
99+
;;
94100
*)
95101
CC_FOR_BUILD=clang
96102
;;

cpython-unix/build.cross.Dockerfile

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,9 +52,11 @@ RUN apt-get install \
5252
gcc-mips-linux-gnu \
5353
gcc-mips64el-linux-gnuabi64 \
5454
gcc-mipsel-linux-gnu \
55+
gcc-s390x-linux-gnu \
5556
libc6-dev-arm64-cross \
5657
libc6-dev-armel-cross \
5758
libc6-dev-armhf-cross \
5859
libc6-dev-mips-cross \
5960
libc6-dev-mips64el-cross \
60-
libc6-dev-mipsel-cross
61+
libc6-dev-mipsel-cross \
62+
libc6-dev-s390x-cross

cpython-unix/build.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -106,6 +106,8 @@ def add_target_env(env, build_platform, target_triple, build_env):
106106
env["CC"] = "mipsel-linux-gnu-gcc"
107107
elif target_triple == "mips64el-unknown-linux-gnuabi64":
108108
env["CC"] = "mips64el-linux-gnuabi64-gcc"
109+
elif target_triple == "s390x-unknown-linux-gnu":
110+
env["CC"] = "s390x-linux-gnu-gcc"
109111
else:
110112
raise Exception("unhandled target triple: %s" % target_triple)
111113

@@ -132,6 +134,8 @@ def add_target_env(env, build_platform, target_triple, build_env):
132134
env["TARGET_TRIPLE"] = "mipsel-unknown-linux-gnu"
133135
elif target_triple == "mips64el-unknown-linux-gnuabi64":
134136
env["TARGET_TRIPLE"] = "mips64el-unknown-linux-gnuabi64"
137+
elif target_triple == "s390x-unknown-linux-gnu":
138+
env["TARGET_TRIPLE"] = "s390x-unknown-linux-gnu"
135139
elif target_triple in ("x86_64-unknown-linux-gnu", "x86_64-unknown-linux-musl"):
136140
env["TARGET_TRIPLE"] = "x86_64-unknown-linux-gnu"
137141
elif target_triple == "i686-unknown-linux-gnu":
Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
# Setup.dist doesn't have entries for all modules. This file defines
2+
# what's missing. The content here is reconstructed from logic in
3+
# setup.py and what was observed to execute in a normal build via setup.py.
4+
# We should audit this every time we upgrade CPython.
5+
6+
_bz2 _bz2module.c -lbz2
7+
_crypt _cryptmodule.c -lcrypt
8+
_ctypes _ctypes/_ctypes.c _ctypes/callbacks.c _ctypes/callproc.c _ctypes/stgdict.c _ctypes/cfield.c -I/tools/deps/include -L/tools/deps/lib -lffi -ldl
9+
_ctypes_test _ctypes/_ctypes_test.c -lm
10+
_curses _cursesmodule.c -DHAVE_NCURSESW=1 -I/tools/deps/include/ncursesw -L/tools/deps/lib -lncursesw
11+
_curses_panel _curses_panel.c -DHAVE_NCURSESW=1 -I/tools/deps/include/ncursesw -L/tools/deps/lib -lpanelw -lncursesw
12+
_dbm _dbmmodule.c -DHAVE_BERKDB_H -DDB_DBM_HSEARCH -I/tools/deps/include -L/tools/deps/lib -ldb
13+
_decimal _decimal/_decimal.c _decimal/libmpdec/basearith.c _decimal/libmpdec/constants.c _decimal/libmpdec/context.c _decimal/libmpdec/convolute.c _decimal/libmpdec/crt.c _decimal/libmpdec/difradix2.c _decimal/libmpdec/fnt.c _decimal/libmpdec/fourstep.c _decimal/libmpdec/io.c _decimal/libmpdec/mpalloc.c _decimal/libmpdec/mpdecimal.c _decimal/libmpdec/numbertheory.c _decimal/libmpdec/sixstep.c _decimal/libmpdec/transpose.c -DCONFIG_64=1 -DANSI=1 -DHAVE_UINT128_T=1 -IModules/_decimal/libmpdec
14+
_elementtree _elementtree.c -DHAVE_EXPAT_CONFIG_H=1 -DXML_POOR_ENTROPY=1 -DUSE_PYEXPAT_CAPI -IModules/expat
15+
_gdbm _gdbmmodule.c -DHAVE_NDBM_H -I/tools/deps/include -L/tools/deps/lib -lgdbm
16+
_hashlib _hashopenssl.c -I/tools/deps/include -L/tools/deps/lib -lssl -lcrypto
17+
_json _json.c
18+
_lsprof _lsprof.c rotatingtree.c
19+
_lzma _lzmamodule.c -I/tools/deps/include -L/tools/deps/lib -llzma
20+
# TODO check setup.py logic for semaphore.c and possibly fix missing
21+
# dependency.
22+
_multiprocessing _multiprocessing/multiprocessing.c _multiprocessing/semaphore.c
23+
_opcode _opcode.c
24+
_posixshmem _multiprocessing/posixshmem.c -IModules/_multiprocessing -lrt
25+
_queue _queuemodule.c
26+
_sqlite3 _sqlite/cache.c _sqlite/connection.c _sqlite/cursor.c _sqlite/microprotocols.c _sqlite/module.c _sqlite/prepare_protocol.c _sqlite/row.c _sqlite/statement.c _sqlite/util.c -I/tools/deps/include -IModules/_sqlite -DMODULE_NAME=\"sqlite3\" -DSQLITE_OMIT_LOAD_EXTENSION=1 -L/tools/deps/lib -lsqlite3
27+
_ssl _ssl.c -I/tools/deps/include -lssl -lcrypto
28+
_testbuffer _testbuffer.c
29+
_testimportmultiple _testimportmultiple.c
30+
_testinternalcapi _testinternalcapi.c -DPy_BUILD_CORE_MODULE
31+
_testmultiphase _testmultiphase.c
32+
_tkinter _tkinter.c tkappinit.c -DWITH_APPINIT -I/tools/deps/include/X11 -L/tools/deps/lib -ltcl8.6 -ltk8.6 -lX11 -lxcb -lXau
33+
_uuid _uuidmodule.c -I/tools/deps/include/uuid -luuid
34+
_xxsubinterpreters _xxsubinterpretersmodule.c
35+
_xxtestfuzz _xxtestfuzz/_xxtestfuzz.c _xxtestfuzz/fuzzer.c
36+
ossaudiodev ossaudiodev.c
37+
pyexpat pyexpat.c expat/xmlparse.c expat/xmlrole.c expat/xmltok.c -DHAVE_EXPAT_CONFIG_H=1 -DXML_POOR_ENTROPY=1 -DUSE_PYEXPAT_CAPI -IModules/expat
38+
# readline variant needs to come first because libreadline is in /tools/deps and is
39+
# picked up by build. We /could/ make libedit first. But since we employ a hack to
40+
# coerce use of libedit on Linux, it seems prudent for the build system to pick
41+
# up readline.
42+
readline VARIANT=readline readline.c -I/tools/deps/include -I/tools/deps/include/ncursesw -L/tools/deps/lib -lreadline -lncursesw
43+
readline VARIANT=libedit readline-libedit.c -DUSE_LIBEDIT=1 -I/tools/deps/libedit/include -I/tools/deps/libedit/include/ncursesw -L/tools/deps/libedit/lib -ledit -lncursesw

cpython-unix/targets.yml

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -215,6 +215,32 @@ mipsel-unknown-linux-gnu:
215215
- zlib
216216
openssl_target: linux-mips32
217217

218+
s390x-unknown-linux-gnu:
219+
host_platforms:
220+
- linux
221+
docker_image_suffix: .cross
222+
needs:
223+
- bdb
224+
- binutils
225+
- bzip2
226+
- gdbm
227+
- libedit
228+
- libffi
229+
- libX11
230+
- libXau
231+
- libxcb
232+
- ncurses
233+
- readline
234+
- sqlite
235+
- tcl
236+
- tk
237+
- tix
238+
- uuid
239+
- xorgproto
240+
- xz
241+
- zlib
242+
openssl_target: linux64-s390x
243+
218244
thumb7k-apple-watchos:
219245
host_platforms:
220246
- darwin

docs/building.rst

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ As are various other targets::
3939
$ ./build-linux.py --target armv7-unknown-linux-gnueabihf
4040
$ ./build-linux.py --target mips-unknown-linux-gnu
4141
$ ./build-linux.py --target mipsel-unknown-linux-gnu
42-
42+
$ ./build-linux.py --target s390x-unknown-linux-gnu
4343

4444
macOS
4545
=====

src/main.rs

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@ const RECOGNIZED_TRIPLES: &[&str] = &[
3333
"mips-unknown-linux-gnu",
3434
"mipsel-unknown-linux-gnu",
3535
"mips64el-unknown-linux-gnuabi64",
36+
"s390x-unknown-linux-gnu",
3637
"thumbv7k-apple-watchos",
3738
"x86_64-apple-darwin",
3839
"x86_64-apple-ios",
@@ -145,6 +146,10 @@ static GLIBC_MAX_VERSION_BY_TRIPLE: Lazy<HashMap<&'static str, version_compare::
145146
"mips64el-unknown-linux-gnuabi64",
146147
version_compare::Version::from("2.17").unwrap(),
147148
);
149+
versions.insert(
150+
"s390x-unknown-linux-gnu",
151+
version_compare::Version::from("2.17").unwrap(),
152+
);
148153
versions.insert(
149154
"x86_64-unknown-linux-gnu",
150155
version_compare::Version::from("2.17").unwrap(),
@@ -173,6 +178,7 @@ static ELF_ALLOWED_LIBRARIES_BY_TRIPLE: Lazy<HashMap<&'static str, Vec<&'static
173178
("mips-unknown-linux-gnu", vec!["ld.so.1"]),
174179
("mipsel-unknown-linux-gnu", vec!["ld.so.1"]),
175180
("mips64el-unknown-linux-gnuabi64", vec![]),
181+
("s390x-unknown-linux-gnu", vec!["ld64.so.1"]),
176182
("x86_64-unknown-linux-gnu", vec!["ld-linux-x86-64.so.2"]),
177183
]
178184
.iter()
@@ -333,6 +339,7 @@ static PLATFORM_TAG_BY_TRIPLE: Lazy<HashMap<&'static str, &'static str>> = Lazy:
333339
("mips-unknown-linux-gnu", "linux-mips"),
334340
("mipsel-unknown-linux-gnu", "linux-mipsel"),
335341
("mips64el-unknown-linux-gnuabi64", "todo"),
342+
("s390x-unknown-linux-gnu", "linux-s390x"),
336343
("x86_64-apple-darwin", "macosx-10.9-x86_64"),
337344
("x86_64-apple-ios", "iOS-x86_64"),
338345
("x86_64-pc-windows-msvc", "win-amd64"),
@@ -370,6 +377,7 @@ fn validate_elf(
370377
"mips-unknown-linux-gnu" => goblin::elf::header::EM_MIPS,
371378
"mipsel-unknown-linux-gnu" => goblin::elf::header::EM_MIPS,
372379
"mips64el-unknown-linux-gnuabi64" => 0,
380+
"s390x-unknown-linux-gnu" => goblin::elf::header::EM_S390,
373381
"x86_64-unknown-linux-gnu" => goblin::elf::header::EM_X86_64,
374382
"x86_64-unknown-linux-musl" => goblin::elf::header::EM_X86_64,
375383
_ => panic!("unhandled target triple: {}", target_triple),
@@ -400,7 +408,7 @@ fn validate_elf(
400408
.expect("max glibc version not defined for target triple");
401409

402410
// functionality doesn't yet support mips.
403-
if !target_triple.starts_with("mips") {
411+
if !target_triple.starts_with("mips") && !target_triple.starts_with("s390x-") {
404412
let mut undefined_symbols = tugger_binary_analysis::find_undefined_elf_symbols(&bytes, elf);
405413
undefined_symbols.sort();
406414

0 commit comments

Comments
 (0)