1 Commits

Author SHA1 Message Date
Ralph Lange
8a2666a9de Update GHA images: remove Ub-16, add Ub-22, macos-12, macos-11
Some checks failed
ci-scripts build/test / Unit tests on macos-10.15 (push) Has been cancelled
ci-scripts build/test / Unit tests on macos-11 (push) Has been cancelled
ci-scripts build/test / Unit tests on macos-12 (push) Has been cancelled
ci-scripts build/test / Unit tests on ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / Unit tests on ubuntu-20.04 (push) Has been cancelled
ci-scripts build/test / Unit tests on ubuntu-22.04 (push) Has been cancelled
ci-scripts build/test / Unit tests on windows-2016 (push) Has been cancelled
ci-scripts build/test / Unit tests on windows-2019 (push) Has been cancelled
ci-scripts build/test / Unit tests on windows-2022 (push) Has been cancelled
ci-scripts build/test / clang / debug / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / clang / debug / ubuntu-20.04 (push) Has been cancelled
ci-scripts build/test / clang / debug / ubuntu-22.04 (push) Has been cancelled
ci-scripts build/test / clang / default / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / clang / default / ubuntu-20.04 (push) Has been cancelled
ci-scripts build/test / clang / default / ubuntu-22.04 (push) Has been cancelled
ci-scripts build/test / clang / static / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / clang / static / ubuntu-20.04 (push) Has been cancelled
ci-scripts build/test / clang / static / ubuntu-22.04 (push) Has been cancelled
ci-scripts build/test / clang / static-debug / ubuntu-20.04 (push) Has been cancelled
ci-scripts build/test / clang / static-debug / ubuntu-22.04 (push) Has been cancelled
ci-scripts build/test / gcc / debug / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / gcc / debug / ubuntu-20.04 (push) Has been cancelled
ci-scripts build/test / clang / debug / macos-10.15 (push) Has been cancelled
ci-scripts build/test / clang / debug / macos-11 (push) Has been cancelled
ci-scripts build/test / clang / debug / macos-12 (push) Has been cancelled
ci-scripts build/test / clang / default / macos-10.15 (push) Has been cancelled
ci-scripts build/test / clang / default / macos-11 (push) Has been cancelled
ci-scripts build/test / clang / default / macos-12 (push) Has been cancelled
ci-scripts build/test / gcc / debug / windows-2016 (push) Has been cancelled
ci-scripts build/test / gcc / debug / windows-2019 (push) Has been cancelled
ci-scripts build/test / gcc / debug / windows-2022 (push) Has been cancelled
ci-scripts build/test / gcc / default / windows-2016 (push) Has been cancelled
ci-scripts build/test / gcc / default / windows-2019 (push) Has been cancelled
ci-scripts build/test / gcc / default / windows-2022 (push) Has been cancelled
ci-scripts build/test / gcc / static / windows-2016 (push) Has been cancelled
ci-scripts build/test / gcc / static / windows-2019 (push) Has been cancelled
ci-scripts build/test / gcc / static-debug / windows-2022 (push) Has been cancelled
ci-scripts build/test / vs2017 / debug / windows-2016 (push) Has been cancelled
ci-scripts build/test / vs2017 / default / windows-2016 (push) Has been cancelled
ci-scripts build/test / vs2017 / static / windows-2016 (push) Has been cancelled
ci-scripts build/test / vs2017 / static-debug / windows-2016 (push) Has been cancelled
ci-scripts build/test / clang / static-debug / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / gcc / debug / ubuntu-22.04 (push) Has been cancelled
ci-scripts build/test / gcc / default / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / gcc / default / ubuntu-20.04 (push) Has been cancelled
ci-scripts build/test / gcc / default / ubuntu-22.04 (push) Has been cancelled
ci-scripts build/test / gcc / static / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / gcc / static / ubuntu-20.04 (push) Has been cancelled
ci-scripts build/test / gcc / static / ubuntu-22.04 (push) Has been cancelled
ci-scripts build/test / gcc / static-debug / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / gcc / static-debug / ubuntu-20.04 (push) Has been cancelled
ci-scripts build/test / gcc / static-debug / ubuntu-22.04 (push) Has been cancelled
ci-scripts build/test / gcc / static / windows-2022 (push) Has been cancelled
ci-scripts build/test / gcc / static-debug / windows-2016 (push) Has been cancelled
ci-scripts build/test / gcc / static-debug / windows-2019 (push) Has been cancelled
ci-scripts build/test / vs2019 / debug / windows-2019 (push) Has been cancelled
ci-scripts build/test / vs2019 / default / windows-2019 (push) Has been cancelled
ci-scripts build/test / vs2019 / static / windows-2019 (push) Has been cancelled
ci-scripts build/test / vs2019 / static-debug / windows-2019 (push) Has been cancelled
ci-scripts build/test / vs2022 / debug / windows-2022 (push) Has been cancelled
ci-scripts build/test / vs2022 / default / windows-2022 (push) Has been cancelled
ci-scripts build/test / vs2022 / static / windows-2022 (push) Has been cancelled
ci-scripts build/test / vs2022 / static-debug / windows-2022 (push) Has been cancelled
ci-scripts build/test / RTEMS4.10 / RTEMS-pc386-qemu (push) Has been cancelled
ci-scripts build/test / RTEMS4.9 / RTEMS-pc386-qemu (push) Has been cancelled
ci-scripts build/test / RTEMS5 / RTEMS-pc686-qemu (push) Has been cancelled
ci-scripts build/test / WINE32 / debug / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / WINE64 / debug / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / WINE32 / default / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / WINE64 / default / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / WINE32 / static / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / WINE64 / static / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / WINE32 / static-debug / ubuntu-18.04 (push) Has been cancelled
ci-scripts build/test / WINE64 / static-debug / ubuntu-18.04 (push) Has been cancelled
2022-07-04 14:14:19 +02:00
7 changed files with 186 additions and 535 deletions

View File

@@ -19,13 +19,13 @@ jobs:
strategy:
fail-fast: false
matrix:
os: [ubuntu-22.04, ubuntu-20.04, windows-2022, windows-2019, macos-12, macos-11]
os: [ubuntu-22.04, ubuntu-20.04, ubuntu-18.04, windows-2022, windows-2019, windows-2016, macos-12, macos-11, macos-10.15]
steps:
- uses: actions/checkout@v3
- uses: actions/checkout@v2
- name: Show initial environment
run: python3 cue-test.py env
run: python cue-test.py env
- name: Run unit tests
run: python3 cue-test.py
run: python cue-test.py
build-linux:
name: ${{ matrix.cmp }} / ${{ matrix.configuration }} / ${{ matrix.os }}
@@ -36,11 +36,11 @@ jobs:
strategy:
fail-fast: false
matrix:
os: [ubuntu-22.04, ubuntu-20.04]
os: [ubuntu-22.04, ubuntu-20.04, ubuntu-18.04]
cmp: [gcc, clang]
configuration: [default, static, debug, static-debug]
steps:
- uses: actions/checkout@v3
- uses: actions/checkout@v2
- name: Prepare and compile dependencies
run: python cue.py prepare
- name: Build main module (example app)
@@ -59,11 +59,11 @@ jobs:
strategy:
fail-fast: false
matrix:
os: [macos-12, macos-11]
os: [macos-12, macos-11, macos-10.15]
cmp: [clang]
configuration: [default, debug]
steps:
- uses: actions/checkout@v3
- uses: actions/checkout@v2
- name: Prepare and compile dependencies
run: python cue.py prepare
- name: Build main module (example app)
@@ -82,18 +82,26 @@ jobs:
strategy:
fail-fast: false
matrix:
os: [windows-2022, windows-2019]
cmp: [gcc, vs2022, vs2019]
os: [windows-2022, windows-2019, windows-2016]
cmp: [gcc, vs2022, vs2019, vs2017]
configuration: [default, static, debug, static-debug]
exclude:
- os: windows-2022
cmp: vs2019
- os: windows-2022
cmp: vs2017
- os: windows-2019
cmp: vs2022
- os: windows-2019
cmp: vs2017
- os: windows-2016
cmp: vs2022
- os: windows-2016
cmp: vs2019
steps:
- uses: actions/checkout@v3
- uses: actions/checkout@v2
- name: Prepare and compile dependencies
run: python cue.py prepare
- name: Build main module (example app)
@@ -103,36 +111,55 @@ jobs:
- name: Collect and show test results
run: python cue.py test-results
build-cross:
name: cross ${{ matrix.cross }} / ${{ matrix.cmp }} / ${{ matrix.configuration }}
runs-on: ubuntu-latest
build-rtems:
name: RTEMS${{ matrix.rtems }} / ${{ matrix.rtems_target }}
runs-on: ubuntu-20.04
env:
CMP: gcc
BCFG: default
CI_CROSS_TARGETS: ${{ matrix.cross }}
TEST: ${{ matrix.test }}
APT: re2c
RTEMS: ${{ matrix.rtems }}
RTEMS_TARGET: ${{ matrix.rtems_target }}
APT: re2c g++-mingw-w64-i686 g++-mingw-w64-x86-64 qemu-system-x86
strategy:
fail-fast: false
matrix:
# configuration: [default, static, debug, static-debug]
configuration: [default]
cross:
- linux-aarch64
- linux-arm@arm-linux-gnueabi
- linux-arm@arm-linux-gnueabihf
- linux-ppc
- linux-ppc64
- win32-x86-mingw
- windows-x64-mingw
- RTEMS-pc386-qemu@4.9
- RTEMS-pc386-qemu@4.10
- RTEMS-pc686-qemu@5
include:
- cross: RTEMS-pc386-qemu@4.10
test: NO
- rtems: "4.9"
rtems_target: RTEMS-pc386-qemu
- rtems: "4.10"
rtems_target: RTEMS-pc386-qemu
- rtems: "5"
rtems_target: RTEMS-pc686-qemu
steps:
- uses: actions/checkout@v3
- uses: actions/checkout@v2
- name: Prepare and compile dependencies
run: python cue.py prepare
- name: Build main module (example app)
run: python cue.py build
- name: Run main module tests
run: python cue.py -T 15M test
- name: Collect and show test results
run: python cue.py test-results
build-wine:
name: WINE${{ matrix.wine }} / ${{ matrix.configuration }} / ${{ matrix.os }}
runs-on: ${{ matrix.os }}
env:
CMP: ${{ matrix.cmp }}
BCFG: ${{ matrix.configuration }}
WINE: ${{ matrix.wine }}
APT: re2c g++-mingw-w64-i686 g++-mingw-w64-x86-64
strategy:
fail-fast: false
matrix:
os: [ubuntu-18.04]
cmp: [gcc]
configuration: [default, static, debug, static-debug]
wine: [32, 64]
steps:
- uses: actions/checkout@v2
- name: Prepare and compile dependencies
run: python cue.py prepare
- name: Build main module (example app)

View File

@@ -95,10 +95,10 @@ for more details.
### [GitHub Actions](https://github.com/)
- 20 parallel runners on Linux/Windows (5 runners on MacOS)
- Ubuntu 18/20/22, MacOS 11/12, Windows Server 2019/2022
- Ubuntu 16/18/20, MacOS 10.15, Windows Server 2016/2019/2022
- Compile natively on Linux (gcc, clang)
- Compile natively on MacOS (clang)
- Compile natively on Windows (gcc/MinGW, Visual Studio 2019/2022)
- Compile natively on Windows (gcc/MinGW, Visual Studio 2017/2019/2022)
- Cross-compile for Windows 32bit and 64bit using MinGW and WINE
- Cross-compile for RTEMS 4.9 and 4.10 (pc386, Base >= 3.15)
- Cross-compile for RTEMS 5 (10 BSPs, Base >= 7.0.5.1)
@@ -189,19 +189,6 @@ Collect the results of your tests and print a summary.
`exec`\
Execute the remainder of the line using the default command shell.
## Extra arguments to `make`
You can add additional arguments to the make runs that the `cue.py` script
starts. Put your additional arguments into environment variables named
`EXTRA`, `EXTRA1`, ... `EXTRA5`.
The variables may contain multiple arguments, separated by whitespace.
Use regular shell script quoting (single/double quotes, backslash escapes)
if you need spaces inside an extra argument.
The YAML syntax needed to set environment variables depends on the CI
service and platform. (See the full example configuration file.)
## Setup Files
Your module might depend on EPICS Base and a few other support modules.
@@ -296,8 +283,8 @@ Feel free to suggest more default settings using a Pull Request.
## RTEMS
Cross-compiling to RTEMS versions 4.9, 4.10 or 5 is supported
on supported CI services. For configuration see below.
Setting `RTEMS` to the RTEMS version number (`4.9`, `4.10` or `5`)
enables cross-compiling to RTEMS on supported CI services.
Tests can also be run cross-platform, using `qemu`.
The RTEMS 5 builds now include most of the BSPs with configuration in Base:
@@ -314,38 +301,15 @@ The RTEMS 5 builds now include most of the BSPs with configuration in Base:
- xilinx_zynq_a9_qemu w/ libbsd
Build configuration [can be found here][ref.rtems5build].
Set `RSB_BUILD` to select the RTEMS toolchain release name/data from
Set `RTEMS_TARGET` to configure the EPICS target architecture and
`RSB_BUILD` to select the RTEMS toolchain release name/data from
https://github.com/mdavidsaver/rsb/releases.
RTEMS 5 builds need to be switched to ubuntu version >= 20
RTEMS 5 builds need to be switched to a newer ubuntu version
(aka. **os: ubuntu-20.04** with GitHub Actions,
**dist: focal** with Travis-CI or
**image: ubuntu:focal** with GitLab CI/CD).
## Cross Compilation
Setting the `CI_CROSS_TARGETS` environment variable enables cross-compiling
from Linux to the provided targets architectures.
The value of the environment variable must contain the EPICS architecture
and - depending on the target - may contain additional information like
the compiler prefix to be used or the version of the target OS.
Multiple cross-targets can be added to the `CI_CROSS_TARGETS` variable
by separating them with a colon (`:`) character.
For example, possible values are:
- linux-aarch64
- linux-arm@arm-linux-gnueabi
- linux-arm@arm-linux-gnueabihf
- linux-ppc
- linux-ppc64
- win32-x86-mingw
- windows-x64-mingw
- RTEMS-pc386-qemu@4.9
- RTEMS-pc386-qemu@4.10
- RTEMS-pc686-qemu@5
## Debugging
Setting `VV=1` in your service configuration (e.g., `.travis.yml`) for a

View File

@@ -8,11 +8,11 @@
from __future__ import print_function
import sys, os, shutil, fileinput
import distutils.util
import re
import subprocess as sp
import unittest
import logging
import fnmatch
from argparse import Namespace
builddir = os.getcwd()
@@ -66,8 +66,6 @@ import cue
# we're working with tags (detached heads) a lot: suppress advice
cue.call_git(['config', '--global', 'advice.detachedHead', 'false'])
# Don't build dependencies when running unit tests
cue.skip_dep_builds = True
class TestSourceSet(unittest.TestCase):
@@ -80,10 +78,10 @@ class TestSourceSet(unittest.TestCase):
def test_EmptySetupDirsPath(self):
del os.environ['SETUP_PATH']
self.assertRaisesRegex(NameError, '\(SETUP_PATH\) is empty', cue.source_set, 'test01')
self.assertRaisesRegexp(NameError, '\(SETUP_PATH\) is empty', cue.source_set, 'test01')
def test_InvalidSetupName(self):
self.assertRaisesRegex(NameError, 'does not exist in SETUP_PATH', cue.source_set, 'xxdoesnotexistxx')
self.assertRaisesRegexp(NameError, 'does not exist in SETUP_PATH', cue.source_set, 'xxdoesnotexistxx')
def test_ValidSetupName(self):
capturedOutput = getStringIO()
@@ -120,7 +118,7 @@ class TestSourceSet(unittest.TestCase):
sys.stdout = capturedOutput
cue.source_set('test03')
sys.stdout = sys.__stdout__
self.assertRegex(capturedOutput.getvalue(), 'Ignoring already included setup file')
self.assertRegexpMatches(capturedOutput.getvalue(), 'Ignoring already included setup file')
class TestUpdateReleaseLocal(unittest.TestCase):
@@ -529,7 +527,7 @@ class TestTravisDetectContext(unittest.TestCase):
sys.stdout = capturedOutput
cue.detect_context()
sys.stdout = sys.__stdout__
self.assertRegex(capturedOutput.getvalue(), "Variable 'STATIC' not supported anymore")
self.assertRegexpMatches(capturedOutput.getvalue(), "Variable 'STATIC' not supported anymore")
def test_MisspelledBcfgGetsWarning(self):
os.environ['BCFG'] = 'static-dubug'
@@ -537,7 +535,7 @@ class TestTravisDetectContext(unittest.TestCase):
sys.stdout = capturedOutput
cue.detect_context()
sys.stdout = sys.__stdout__
self.assertRegex(capturedOutput.getvalue(), "Unrecognized build configuration setting")
self.assertRegexpMatches(capturedOutput.getvalue(), "Unrecognized build configuration setting")
@unittest.skipIf(ci_service != 'appveyor', 'Run appveyor tests only on appveyor')
@@ -690,7 +688,7 @@ class TestAppveyorDetectContext(unittest.TestCase):
sys.stdout = capturedOutput
cue.detect_context()
sys.stdout = sys.__stdout__
self.assertRegex(capturedOutput.getvalue(), "Variable 'STATIC' not supported anymore")
self.assertRegexpMatches(capturedOutput.getvalue(), "Variable 'STATIC' not supported anymore")
def test_MisspelledConfigurationGetsWarning(self):
os.environ['CONFIGURATION'] = 'static-dubug'
@@ -698,11 +696,12 @@ class TestAppveyorDetectContext(unittest.TestCase):
sys.stdout = capturedOutput
cue.detect_context()
sys.stdout = sys.__stdout__
self.assertRegex(capturedOutput.getvalue(), "Unrecognized build configuration setting")
self.assertRegexpMatches(capturedOutput.getvalue(), "Unrecognized build configuration setting")
class TestSetupForBuild(unittest.TestCase):
args = Namespace(paths=[])
cue.building_base = True
if ci_os == 'windows':
choco_installs = ['make']
if ci_service != 'appveyor':
@@ -710,7 +709,6 @@ class TestSetupForBuild(unittest.TestCase):
sp.check_call(['choco', 'install', '-ry'] + choco_installs)
def setUp(self):
cue.building_base = True
if ci_service == 'appveyor':
os.environ['CONFIGURATION'] = 'default'
cue.detect_context()
@@ -840,7 +838,7 @@ class TestSetupForBuild(unittest.TestCase):
def test_ExtraMakeArgs(self):
os.environ['EXTRA'] = 'bla'
for ind in range(1,5):
os.environ['EXTRA{0}'.format(ind)] = '"bla {0}"'.format(ind)
os.environ['EXTRA{0}'.format(ind)] = 'bla {0}'.format(ind)
cue.setup_for_build(self.args)
self.assertTrue(cue.extra_makeargs[0] == 'bla', 'Extra make arg [0] not set')
for ind in range(1,5):
@@ -885,77 +883,6 @@ LINE2=NO''')
cue.extract_archive(hook, cwd=self.location)
self.assertTrue(os.path.exists(self.new_file), "archive extract didn't add new file")
@unittest.skipIf(ci_os != 'linux', 'CrossCompatibilityHandling tests only apply to linux')
class TestCrossCompatibilityHandling(unittest.TestCase):
args = Namespace(paths=[])
def setUp(self):
cue.clear_lists()
os.environ.pop('CI_CROSS_TARGETS', None)
os.environ.pop('RTEMS_TARGET', None)
os.environ.pop('RTEMS', None)
os.environ.pop('WINE', None)
os.environ['MODULES'] = ''
cue.detect_context()
# Make cue.prepare() reconfigure base
for root, dirs, files in os.walk(cue.ci['cachedir']):
if 'checked_out' in files:
if fnmatch.fnmatch(root, '*/base-*'):
os.remove(os.path.join(root, 'checked_out'))
def runtest_rtems(self, arch, ver):
cue.prepare(self.args)
self.assertTrue('CI_CROSS_TARGETS' in os.environ, "CI_CROSS_TARGETS has not been set")
self.assertTrue(os.environ['CI_CROSS_TARGETS'].startswith(':' + arch),
"CI_CROSS_TARGETS is {0} (expected: :{1}...)"
.format(os.environ['CI_CROSS_TARGETS'], arch))
self.assertTrue(os.environ['CI_CROSS_TARGETS'].endswith('@' + ver),
"CI_CROSS_TARGETS is {0} (expected: ...@{1})"
.format(os.environ['CI_CROSS_TARGETS'], ver))
def test_RTEMS49_no_target(self):
os.environ['RTEMS'] = '4.9'
self.runtest_rtems('RTEMS-pc386', '4.9')
def test_RTEMS49_with_target(self):
os.environ['RTEMS'] = '4.9'
os.environ['RTEMS_TARGET'] = 'RTEMS-pc386'
self.runtest_rtems('RTEMS-pc386', '4.9')
def test_RTEMS410_no_target(self):
os.environ['RTEMS'] = '4.10'
self.runtest_rtems('RTEMS-pc386', '4.10')
def test_RTEMS410_with_target(self):
os.environ['RTEMS'] = '4.10'
os.environ['RTEMS_TARGET'] = 'RTEMS-pc386'
self.runtest_rtems('RTEMS-pc386', '4.10')
def test_RTEMS5_no_target(self):
os.environ['RTEMS'] = '5'
self.runtest_rtems('RTEMS-pc686', '5')
def test_RTEMS5_with_target(self):
os.environ['RTEMS'] = '5'
os.environ['RTEMS_TARGET'] = 'RTEMS-pc686'
self.runtest_rtems('RTEMS-pc686', '5')
def test_WINE32(self):
os.environ['WINE'] = '32'
cue.prepare(self.args)
self.assertTrue('CI_CROSS_TARGETS' in os.environ, "CI_CROSS_TARGETS has not been set")
self.assertEqual(os.environ['CI_CROSS_TARGETS'], ':win32-x86-mingw',
"CI_CROSS_TARGETS is {0} (expected: :win32-x86-mingw)"
.format(os.environ['CI_CROSS_TARGETS']))
def test_WINE64(self):
os.environ['WINE'] = '64'
cue.prepare(self.args)
self.assertTrue('CI_CROSS_TARGETS' in os.environ, "CI_CROSS_TARGETS has not been set")
self.assertEqual(os.environ['CI_CROSS_TARGETS'], ':windows-x64-mingw',
"CI_CROSS_TARGETS is {0} (expected: :windows-x64-mingw)"
.format(os.environ['CI_CROSS_TARGETS']))
if __name__ == "__main__":
if 'VV' in os.environ and os.environ['VV'] == '1':

425
cue.py
View File

@@ -1,19 +1,17 @@
#!/usr/bin/env python
"""EPICS CI build script for Linux/MacOS/Windows on Travis/GitLab/AppVeyor/GitHub-Actions
"""CI build script for Linux/MacOS/Windows on Travis/AppVeyor/GitHub-Actions
"""
from __future__ import print_function
import sys, os, stat, shlex, shutil
import sys, os, stat, shutil
import fileinput
import logging
import re
import time
import threading
from glob import glob
import subprocess as sp
import sysconfig
import shutil
import distutils.util
logger = logging.getLogger(__name__)
@@ -33,11 +31,6 @@ def log_modified():
sys.stdout.write(F.read())
sys.stdout.write(os.linesep)
def whereis(cmd):
if hasattr(shutil, 'which'): # >= py3.3
loc = shutil.which(cmd)
print('{0}Found exec {1} at {2!r} {3}'.format(ANSI_CYAN, cmd, loc, ANSI_RESET))
def prepare_env():
'''HACK
github actions yaml configuration doesn't allow
@@ -170,20 +163,17 @@ modules_to_compile = []
setup = {}
places = {}
extra_makeargs = []
make_timeout = 0.
is_base314 = False
is_make3 = False
has_test_results = False
silent_dep_builds = True
skip_dep_builds = False
do_recompile = False
installed_7z = False
def clear_lists():
global is_base314, has_test_results, silent_dep_builds, is_make3
global _modified_files, do_recompile, building_base
del seen_setups[:]
del modules_to_compile[:]
del extra_makeargs[:]
@@ -194,8 +184,6 @@ def clear_lists():
has_test_results = False
silent_dep_builds = True
do_recompile = False
building_base = False
_modified_files = set()
ci['service'] = '<none>'
ci['os'] = '<unknown>'
ci['platform'] = '<unknown>'
@@ -215,8 +203,9 @@ clear_lists()
if 'BASE' in os.environ and os.environ['BASE'] == 'SELF':
building_base = True
skip_dep_builds = True
places['EPICS_BASE'] = curdir
else:
building_base = False
# Setup ANSI Colors
ANSI_RED = "\033[31;1m"
@@ -320,7 +309,7 @@ def host_info():
print('PYTHONPATH')
for dname in sys.path:
print(' ', dname)
print('platform =', sysconfig.get_platform())
print('platform =', distutils.util.get_platform())
if ci['os'] == 'windows':
print('{0}Available Visual Studio versions{1}'.format(ANSI_CYAN, ANSI_RESET))
@@ -618,21 +607,15 @@ def add_dependency(dep):
if dep + '_HOOK' in setup:
hook = setup[dep + '_HOOK']
hook_file = os.path.join(curdir, hook)
hook_ext = os.path.splitext(hook_file)[1]
if os.path.exists(hook_file):
if hook_ext == '.patch':
if re.match(r'.+\.patch$', hook):
apply_patch(hook_file, cwd=place)
elif hook_ext in ('.zip', '.7z'):
elif re.match(r'.+\.(zip|7z)$', hook):
extract_archive(hook_file, cwd=place)
elif hook_ext == '.py':
print('Running py hook {0} in {1}'.format(hook, place))
sp.check_call([sys.executable, hook_file], cwd=place)
else:
print('Running hook {0} in {1}'.format(hook, place))
sys.stdout.flush()
sp.check_call(hook_file, shell=True, cwd=place)
else:
print('Skipping invalid hook {0} in {1}'.format(hook, place))
# write checked out commit hash to marker file
head = get_git_hash(place)
@@ -693,10 +676,8 @@ def setup_for_build(args):
if ci['os'] == 'windows':
if os.path.exists(r'C:\Strawberry\perl\bin'):
# Put strawberry perl in front of the PATH (so that Git Perl is further behind)
# Put Chocolatey\bin ahead to select correct make.exe
logger.debug('Adding Strawberry Perl in front of the PATH')
os.environ['PATH'] = os.pathsep.join([r'C:\ProgramData\Chocolatey\bin',
r'C:\Strawberry\c\bin',
os.environ['PATH'] = os.pathsep.join([r'C:\Strawberry\c\bin',
r'C:\Strawberry\perl\site\bin',
r'C:\Strawberry\perl\bin',
os.environ['PATH']])
@@ -764,6 +745,14 @@ def setup_for_build(args):
if re.match('^test-results:', line):
has_test_results = True
# Check make version
if re.match(r'^GNU Make 3', sp.check_output(['make', '-v']).decode('ascii')):
is_make3 = True
logger.debug('Check if make is a 3.x series: %s', is_make3)
# apparently %CD% is handled automagically
os.environ['TOP'] = os.getcwd()
addpaths = []
for path in args.paths:
try:
@@ -775,23 +764,11 @@ def setup_for_build(args):
os.environ['PATH'] = os.pathsep.join([os.environ['PATH']] + addpaths)
logger.debug('Final PATH')
for loc in os.environ['PATH'].split(os.pathsep):
logger.debug(' %r', loc)
# Check make version
if re.match(r'^GNU Make 3', sp.check_output(['make', '-v']).decode('ascii')):
is_make3 = True
logger.debug('Check if make is a 3.x series: %s', is_make3)
# apparently %CD% is handled automagically
os.environ['TOP'] = os.getcwd()
# Add EXTRA make arguments
for tag in ['EXTRA', 'EXTRA1', 'EXTRA2', 'EXTRA3', 'EXTRA4', 'EXTRA5']:
val = os.environ.get(tag, "")
if len(val)>0:
extra_makeargs.extend(shlex.split(val))
extra_makeargs.append(val)
def fix_etc_hosts():
@@ -809,266 +786,6 @@ def fix_etc_hosts():
logger.debug('EXEC DONE')
def edit_make_file(mode, path, values):
"""Edit an EPICS Make file.
mode should be either "a" or "w", as for the open function.
path should be a list, e.g. ["configure", "CONFIG_SITE"]
values should be a dictionary of values to edit. If the value starts with
a "+" the value will be appended.
Example usage:
edit_make_file("a", ["configure", "CONFIG_SITE"], {
"VARIABLE": "value",
"APPENDED_VARIABLE": "+value",
})
"""
with open(os.path.join(places["EPICS_BASE"], *path), mode) as f:
for variable, value in values.items():
if value.startswith("+"):
op = "+="
value = value[1:]
else:
op = "="
f.write(variable + op + value + "\n")
def handle_old_cross_variables():
if "CI_CROSS_TARGETS" not in os.environ:
os.environ["CI_CROSS_TARGETS"] = ""
if "RTEMS" in os.environ:
if 'RTEMS_TARGET' in os.environ:
rtems_target = os.environ['RTEMS_TARGET']
else:
if os.environ['RTEMS'] == '5':
rtems_target = 'RTEMS-pc686-qemu'
else:
rtems_target = 'RTEMS-pc386'
if os.path.exists(os.path.join(places['EPICS_BASE'], 'configure', 'os',
'CONFIG.Common.RTEMS-pc386-qemu')):
# Base 3.15 doesn't have -qemu target architecture
rtems_target = 'RTEMS-pc386-qemu'
new_cross_target = ":" + rtems_target + "@" + os.environ["RTEMS"]
os.environ["CI_CROSS_TARGETS"] += new_cross_target
print(
"{0}WARNING: deprecated RTEMS environment variable was specified." \
" Please add '{1}' to CI_CROSS_TARGETS instead.{2}".format(
ANSI_RED, new_cross_target, ANSI_RESET
)
)
logger.debug('Replaced deprecated RTEMS target with new entry in CI_CROSS_TARGETS: %s', new_cross_target)
if "WINE" in os.environ:
if os.environ['WINE'] == '32':
new_cross_target = ":win32-x86-mingw"
else:
new_cross_target = ":windows-x64-mingw"
os.environ["CI_CROSS_TARGETS"] += new_cross_target
print(
"{0}WARNING: deprecated WINE environment variable was specified." \
" Please add '{1}' to CI_CROSS_TARGETS instead.{2}".format(
ANSI_RED, new_cross_target, ANSI_RESET
)
)
logger.debug('Replaced deprecated WINE target with new entry in CI_CROSS_TARGETS: %s', new_cross_target)
def prepare_cross_compilation(cross_target_info):
"""Prepare the configuration for a single value of the CI_CROSS_TARGETS
variable.
See the README.md file for more information on this variable."""
cross_target_info = cross_target_info.split("@")
if len(cross_target_info) == 2:
target_param = cross_target_info[1]
else:
target_param = None
target = cross_target_info[0]
if target.startswith("RTEMS-"):
prepare_rtems_cross(target, target_param)
elif target.endswith("-mingw"):
prepare_wine_cross(target)
elif target.startswith("linux-"):
prepare_linux_cross(target, target_param)
else:
raise ValueError(
"Unknown CI_CROSS_TARGETS {0}. "
"Please see the ci-scripts README for available values.".format(target)
)
def prepare_rtems_cross(epics_arch, version):
"""Prepare the configuration for RTEMS cross-compilation for the given
RTEMS version.
If version is None, it defaults to version 5 for RTEMS-pc686-*, 4.10
otherwise."""
if version is None:
if epics_arch.startswith("RTEMS-pc686"):
version = "5"
else:
version = "4.10"
# eg. "RTEMS-pc386" or "RTEMS-pc386-qemu" -> "pc386"
rtems_bsp = re.match("^RTEMS-([^-]*)(?:-qemu)?$", epics_arch).group(1)
print("Cross compiler RTEMS{0} @ {1}".format(version, epics_arch))
if ci["os"] == "linux":
download_rtems(version, rtems_bsp)
edit_make_file(
"a",
["configure", "os", "CONFIG_SITE.Common.RTEMS"],
{
"RTEMS_VERSION": version,
"RTEMS_BASE": "/opt/rtems/" + version,
},
)
edit_make_file(
"a",
["configure", "CONFIG_SITE"],
{"CROSS_COMPILER_TARGET_ARCHS": epics_arch},
)
ci["apt"].extend(
["re2c", "g++-mingw-w64-i686", "g++-mingw-w64-x86-64", "qemu-system-x86"]
)
def download_rtems(version, rtems_bsp):
rsb_release = os.environ.get("RSB_BUILD", "20210306")
tar_name = "{0}-rtems{1}.tar.xz".format(rtems_bsp, version)
print("Downloading RTEMS {0} cross compiler: {1}".format(version, tar_name))
sys.stdout.flush()
sp.check_call(
[
"curl",
"-fsSL",
"--retry",
"3",
"-o",
tar_name,
"https://github.com/mdavidsaver/rsb/releases/download/{0}%2F{1}/{2}".format(
version, rsb_release, tar_name
),
],
cwd=toolsdir,
)
sudo_prefix = []
if ci["service"] == "github-actions":
sudo_prefix = ["sudo"]
sp.check_call(
sudo_prefix + ["tar", "-C", "/", "-xmJ", "-f", os.path.join(toolsdir, tar_name)]
)
os.remove(os.path.join(toolsdir, tar_name))
for rtems_cc in glob("/opt/rtems/*/bin/*-gcc"):
print("{0}{1} --version{2}".format(ANSI_CYAN, rtems_cc, ANSI_RESET))
sys.stdout.flush()
sp.check_call([rtems_cc, "--version"])
def prepare_wine_cross(epics_arch):
"""Prepare the configuration for Wine cross-compilation for the given mingw
architecture."""
if epics_arch == "win32-x86-mingw":
gnu_arch = "i686-w64-mingw32"
deb_arch = "mingw-w64-i686"
bits = "32"
elif epics_arch == "windows-x64-mingw":
gnu_arch = "x86_64-w64-mingw32"
deb_arch = "mingw-w64-x86-64"
bits = "64"
else:
raise ValueError(
"Unknown architecture '{0}' for WINE target. "
"Please see the ci-scripts README for available values.".format(epics_arch)
)
print("Cross compiler mingw{} / Wine".format(bits))
edit_make_file(
"a",
["configure", "os", "CONFIG.linux-x86." + epics_arch],
{"CMPLR_PREFIX": gnu_arch + "-"},
)
edit_make_file(
"a",
["configure", "CONFIG_SITE"],
{"CROSS_COMPILER_TARGET_ARCHS": "+" + epics_arch},
)
ci['apt'].extend(["re2c", "g++-" + deb_arch])
def prepare_linux_cross(epics_arch, gnu_arch):
"""Prepare the configuration for Linux cross-compilation for the given
architecture.
If gnu_arch is None, this function will try to guess it using the
epics_arch value.
linux-arm architecture defaults to arm-linux-gnueabi (soft floats)."""
# This list is kind of an intersection between the set of cross-compilers
# provided by Ubuntu[1] and the list of architectures found in
# `epics-base/configure/os`
#
# [1]: https://packages.ubuntu.com/source/focal/gcc-10-cross
if gnu_arch is None:
if epics_arch == "linux-x86":
gnu_arch = "i686-linux-gnu"
elif epics_arch == "linux-arm":
gnu_arch = "arm-linux-gnueabi"
elif epics_arch == "linux-aarch64":
gnu_arch = "aarch64-linux-gnu"
elif epics_arch == "linux-ppc":
gnu_arch = "powerpc-linux-gnu"
elif epics_arch == "linux-ppc64":
gnu_arch = "powerpc64le-linux-gnu"
else:
raise ValueError(
"Could not guess the GNU architecture for EPICS arch: {}. "
"Please use the '@' syntax of the 'CI_CROSS_TARGETS' variable".format(
epics_arch
)
)
print(
"Setting up Linux cross-compiling arch {0} with GNU arch {1}".format(
epics_arch, gnu_arch
)
)
edit_make_file(
"w",
["configure", "os", "CONFIG_SITE.linux-x86_64." + epics_arch],
{
"GNU_TARGET": gnu_arch,
"COMMANDLINE_LIBRARY": "EPICS",
},
)
edit_make_file(
"a",
["configure", "CONFIG_SITE"],
{"CROSS_COMPILER_TARGET_ARCHS": "+" + epics_arch},
)
ci["apt"].extend(["re2c", "g++-" + gnu_arch])
def prepare(args):
host_info()
@@ -1114,8 +831,20 @@ def prepare(args):
elif ci['compiler'].startswith('gcc'):
cxx = re.sub(r'gcc', r'g++', ci['compiler'])
if not os.path.isdir(toolsdir):
os.makedirs(toolsdir)
# Cross compilation on Linux to RTEMS (set RTEMS to version "4.9", "4.10")
# requires qemu, bison, flex, texinfo, install-info
# rtems_bsp is needed also if Base is from cache
if 'RTEMS' in os.environ:
if 'RTEMS_TARGET' in os.environ:
rtems_target = os.environ['RTEMS_TARGET']
elif os.path.exists(os.path.join(places['EPICS_BASE'], 'configure', 'os',
'CONFIG.Common.RTEMS-pc386-qemu')):
# Base 3.15 doesn't have -qemu target architecture
rtems_target = 'RTEMS-pc386-qemu'
else:
rtems_target = 'RTEMS-pc386'
# eg. "RTEMS-pc386" or "RTEMS-pc386-qemu" -> "pc386"
rtems_bsp = re.match('^RTEMS-([^-]*)(?:-qemu)?$', rtems_target).group(1)
if 'BASE' in modules_to_compile or building_base:
fold_start('set.up.epics_build', 'Configuring EPICS build system')
@@ -1166,12 +895,44 @@ endif''')
# Cross-compilations from Linux platform
if ci['os'] == 'linux':
handle_old_cross_variables()
for cross_target_info in os.environ.get("CI_CROSS_TARGETS", "").split(":"):
if cross_target_info == "":
continue
prepare_cross_compilation(cross_target_info)
# Cross compilation to Windows/Wine (set WINE to architecture "32", "64")
# requires wine and g++-mingw-w64-i686 / g++-mingw-w64-x86-64
if 'WINE' in os.environ:
if os.environ['WINE'] == '32':
print('Cross compiler mingw32 / Wine')
with open(os.path.join(places['EPICS_BASE'], 'configure', 'os',
'CONFIG.linux-x86.win32-x86-mingw'), 'a') as f:
f.write('''
CMPLR_PREFIX=i686-w64-mingw32-''')
with open(os.path.join(places['EPICS_BASE'], 'configure', 'CONFIG_SITE'), 'a') as f:
f.write('''
CROSS_COMPILER_TARGET_ARCHS+=win32-x86-mingw''')
if os.environ['WINE'] == '64':
print('Cross compiler mingw64 / Wine')
with open(os.path.join(places['EPICS_BASE'], 'configure', 'os',
'CONFIG.linux-x86.windows-x64-mingw'), 'a') as f:
f.write('''
CMPLR_PREFIX=x86_64-w64-mingw32-''')
with open(os.path.join(places['EPICS_BASE'], 'configure', 'CONFIG_SITE'), 'a') as f:
f.write('''
CROSS_COMPILER_TARGET_ARCHS += windows-x64-mingw''')
# Cross compilation on Linux to RTEMS (set RTEMS to version "4.9", "4.10")
# requires qemu, bison, flex, texinfo, install-info
if 'RTEMS' in os.environ:
print('Cross compiler RTEMS{0} @ {1}'.format(os.environ['RTEMS'], rtems_target))
with open(os.path.join(places['EPICS_BASE'], 'configure', 'os',
'CONFIG_SITE.Common.RTEMS'), 'a') as f:
f.write('''
RTEMS_VERSION={0}
RTEMS_BASE=/opt/rtems/{0}'''.format(os.environ['RTEMS']))
with open(os.path.join(places['EPICS_BASE'], 'configure', 'CONFIG_SITE'), 'a') as f:
f.write('''
CROSS_COMPILER_TARGET_ARCHS += {0}
'''.format(rtems_target))
print('Host compiler', ci['compiler'])
@@ -1221,27 +982,14 @@ PERL = C:/Strawberry/perl/bin/perl -CSD'''
with open(os.path.join(places['EPICS_BASE'], 'configure', 'CONFIG_SITE'), 'a') as f:
f.write(extra_config)
# enable color in error and warning messages if the (cross) compiler supports it
with open(os.path.join(places['EPICS_BASE'], 'configure', 'CONFIG'), 'a') as f:
f.write('''
ifdef T_A
COLOR_FLAG_$(T_A) := $(shell $(CPP) -fdiagnostics-color -E - </dev/null >/dev/null 2>/dev/null && echo -fdiagnostics-color)
USR_CPPFLAGS += $(COLOR_FLAG_$(T_A))
endif''')
fold_end('set.up.epics_build', 'Configuring EPICS build system')
if not os.path.isdir(toolsdir):
os.makedirs(toolsdir)
if ci['os'] == 'windows' and ci['choco']:
fold_start('install.choco', 'Installing CHOCO packages')
for i in range(0,3):
try:
sp.check_call(['choco', 'install'] + ci['choco'] + ['-y', '--limitoutput', '--no-progress'])
except Exception as e:
print(e)
print("Retrying choco install attempt {} after 30 seconds".format(i+1))
time.sleep(30)
else:
break
sp.check_call(['choco', 'install'] + ci['choco'] + ['-y', '--limitoutput', '--no-progress'])
fold_end('install.choco', 'Installing CHOCO packages')
if ci['os'] == 'linux' and ci['apt']:
@@ -1255,31 +1003,46 @@ endif''')
sp.check_call(['brew', 'install'] + ci['homebrew'])
fold_end('install.homebrew', 'Installing Homebrew packages')
if ci['os'] == 'linux' and 'RTEMS' in os.environ:
rsb_release = os.environ.get('RSB_BUILD', '20210306')
tar_name = '{0}-rtems{1}.tar.xz'.format(rtems_bsp, os.environ['RTEMS'])
print('Downloading RTEMS {0} cross compiler: {1}'
.format(os.environ['RTEMS'], tar_name))
sys.stdout.flush()
sp.check_call(['curl', '-fsSL', '--retry', '3', '-o', tar_name,
'https://github.com/mdavidsaver/rsb/releases/download/{0}%2F{1}/{2}'
.format(os.environ['RTEMS'], rsb_release, tar_name)],
cwd=toolsdir)
sudo_prefix = []
if ci['service'] == 'github-actions':
sudo_prefix = ['sudo']
sp.check_call(sudo_prefix + ['tar', '-C', '/', '-xmJ', '-f', os.path.join(toolsdir, tar_name)])
os.remove(os.path.join(toolsdir, tar_name))
for rtems_cc in glob('/opt/rtems/*/bin/*-gcc'):
print('{0}{1} --version{2}'.format(ANSI_CYAN, rtems_cc, ANSI_RESET))
sys.stdout.flush()
sp.check_call([rtems_cc, '--version'])
setup_for_build(args)
print('{0}EPICS_HOST_ARCH = {1}{2}'.format(ANSI_CYAN, os.environ['EPICS_HOST_ARCH'], ANSI_RESET))
whereis('make')
print('{0}$ make --version{1}'.format(ANSI_CYAN, ANSI_RESET))
sys.stdout.flush()
call_make(['--version'], parallel=0)
whereis('perl')
print('{0}$ perl --version{1}'.format(ANSI_CYAN, ANSI_RESET))
sys.stdout.flush()
sp.check_call(['perl', '--version'])
if re.match(r'^vs', ci['compiler']):
whereis('cl')
print('{0}$ cl{1}'.format(ANSI_CYAN, ANSI_RESET))
sys.stdout.flush()
sp.check_call(['cl'])
else:
cc = ci['compiler']
whereis(cc)
print('{0}$ {1} --version{2}'.format(ANSI_CYAN, cc, ANSI_RESET))
sys.stdout.flush()
sp.check_call([cc, '--version'])
if cxx:
whereis(cxx)
print('{0}$ {1} --version{2}'.format(ANSI_CYAN, cxx, ANSI_RESET))
sys.stdout.flush()
sp.check_call([cxx, '--version'])
@@ -1287,7 +1050,7 @@ endif''')
if logging.getLogger().isEnabledFor(logging.DEBUG):
log_modified()
if not skip_dep_builds:
if not building_base:
fold_start('build.dependencies', 'Build missing/outdated dependencies')
for mod in modules_to_compile:
place = places[setup[mod + "_VARNAME"]]

View File

@@ -18,7 +18,7 @@ NTYPES_REPONAME=normativeTypesCPP
NTYPES_REPOOWNER=epics-base
# Sequencer
SNCSEQ_REPOURL=https://github.com/mdavidsaver/sequencer-mirror.git
SNCSEQ_REPOURL=https://www-csr.bessy.de/control/SoftDist/sequencer/repo/branch-2-2.git
SNCSEQ_DEPTH=0
SNCSEQ_DIRNAME=seq

View File

@@ -3,10 +3,10 @@
## Features
- 20 parallel runners on Linux/Windows (5 runners on MacOS)
- Ubuntu 18/20/22, MacOS 11/12, Windows Server 2019/2022
- Ubuntu 16/18/20, MacOS 10.15, Windows Server 2016/2019
- Compile natively on Linux (gcc, clang)
- Compile natively on MacOS (clang)
- Compile natively on Windows (gcc/MinGW, Visual Studio 2019/2022)
- Compile natively on Windows (gcc/MinGW, Visual Studio 2017/2019/2022)
- Cross-compile for Windows 32bit and 64bit using MinGW and WINE
- Cross-compile for RTEMS 4.9 and 4.10 (pc386, Base >= 3.15)
- Cross-compile for RTEMS 5 (10 BSPs, Base >= 7.0.5.1)

View File

@@ -119,15 +119,20 @@ jobs:
configuration: default
name: "Ub-20 clang-10"
- os: macos-11
- os: macos-latest
cmp: clang
configuration: default
name: "MacOS clang-13"
name: "MacOS clang-12"
- os: macos-12
cmp: clang
- os: windows-2016
cmp: vs2017
configuration: default
name: "MacOS clang-13"
name: "Win2016 MSC-17"
- os: windows-2016
cmp: vs2017
configuration: static
name: "Win2016 MSC-17, static"
- os: windows-2019
cmp: gcc
@@ -160,7 +165,7 @@ jobs:
name: "Win2022 MSC-22, static"
steps:
- uses: actions/checkout@v3
- uses: actions/checkout@v2
with:
submodules: true
- name: Automatic core dumper analysis
@@ -182,7 +187,7 @@ jobs:
- name: Build main module
run: python .ci/cue.py build
- name: Run main module tests
run: python .ci/cue.py -T 15M test
run: python .ci/cue.py test
- name: Upload tapfiles Artifact
uses: actions/upload-artifact@v2
with:
@@ -190,38 +195,3 @@ jobs:
path: '**/O.*/*.tap'
- name: Collect and show test results
run: python .ci/cue.py test-results
build-cross:
name: cross ${{ matrix.cross }} / ${{ matrix.cmp }} / ${{ matrix.configuration }}
runs-on: ubuntu-20.04
env:
CMP: gcc
BCFG: default
CI_CROSS_TARGETS: ${{ matrix.cross }}
APT: re2c
strategy:
fail-fast: false
matrix:
# configuration: [default, static, debug, static-debug]
configuration: [default]
cross:
- linux-aarch64
- linux-arm@arm-linux-gnueabi
- linux-arm@arm-linux-gnueabihf
- linux-ppc
- linux-ppc64
- win32-x86-mingw
- windows-x64-mingw
- RTEMS-pc386-qemu@4.9
- RTEMS-pc386-qemu@4.10
- RTEMS-pc686-qemu@5
steps:
- uses: actions/checkout@v3
- name: Prepare and compile dependencies
run: python cue.py prepare
- name: Build main module
run: python cue.py build
- name: Run main module tests
run: python cue.py -T 15M test
- name: Collect and show test results
run: python cue.py test-results