Skip to content

Commit c506a3a

Browse files
authored
Add test configuration (ARMmbed#111)
* Add mbed-bootloader-cliapp tests * Revamp Jenkinsfile code - Make Jenkinsfile less hard coded - to make it easy to add tests - to parallelise as much as possibly - delete dead code - Checkout and deploy source code only once to reduce github usage * Add separate header app tests * Clean up PAL config * Move power cut test app-config * Improve circle script - use v2 config - use a docker image so no setup time - use proper caching so job runs fast * Add nrf52 build tests
1 parent 14d6230 commit c506a3a

13 files changed

+546
-165
lines changed

Jenkinsfile

Lines changed: 221 additions & 101 deletions
Original file line numberDiff line numberDiff line change
@@ -12,135 +12,255 @@
1212
// from ARM Limited or its affiliates.
1313
//----------------------------------------------------------------------------
1414

15-
properties ([[
16-
$class: 'ParametersDefinitionProperty',
17-
parameterDefinitions: [[
18-
$class: 'StringParameterDefinition',
19-
name: 'mbed_os_revision',
20-
defaultValue: 'master',
21-
description: 'Revision of mbed-os to build'
22-
]]
23-
]])
24-
25-
// There seems to be a bug in Jenkins, the first build of every branch fails due to missing parameters.
26-
try {
27-
echo "Verifying build with mbed-os version ${mbed_os_revision}"
28-
env.MBED_OS_REVISION = "${mbed_os_revision}"
29-
} catch (err) {
30-
def mbed_os_revision = "master"
31-
echo "Verifying build with mbed-os version ${mbed_os_revision}"
32-
env.MBED_OS_REVISION = "${mbed_os_revision}"
33-
}
34-
35-
def test_dependencies = []
36-
37-
def test_filters = [
38-
]
39-
40-
def mbed_app_json = ""
41-
42-
def repoName = "mbed-bootloader-internal"
15+
repoName = "mbed-bootloader-internal"
4316

44-
// List of targets to compile
45-
def targets = [
46-
"K64F": ["default"],
47-
"NUCLEO_F429ZI": ["default"],
48-
"UBLOX_EVK_ODIN_W2": ["default"]
49-
]
50-
51-
// Map morpheus toolchains to compiler labels on Jenkins
52-
def toolchains = [
17+
toolchains = [
5318
ARM: "armcc",
5419
GCC_ARM: "arm-none-eabi-gcc",
5520
IAR: "iar_arm"
5621
]
5722

58-
def configurations = [
59-
"default": "mbed_app.json"
60-
]
23+
// RaaS allocation timeout
24+
raas_timeout = 1200
6125

6226
// Initial maps for parallel build steps
6327
def stepsForParallel = [:]
6428

65-
// Jenkins pipeline does not support map.each, we need to use oldschool for loop
66-
for (int i = 0; i < targets.size(); i++) {
67-
for(int j = 0; j < toolchains.size(); j++) {
68-
for(int k = 0; k < configurations.size(); k++) {
69-
def target = targets.keySet().asList().get(i)
70-
def allowed_configs = targets.get(target)
71-
def toolchain = toolchains.keySet().asList().get(j)
72-
def compilerLabel = toolchains.get(toolchain)
73-
def configName = configurations.keySet().asList().get(k)
74-
def config = configurations.get(configName)
75-
def stepName = "${target} ${toolchain} ${configName}"
76-
if(allowed_configs.contains(configName)){
77-
stepsForParallel[stepName] = morpheusBuildStep(target,
78-
compilerLabel,
79-
toolchain,
80-
config,
81-
configName,
82-
repoName,
83-
test_filters,
84-
test_dependencies,
85-
mbed_app_json)
29+
def deployCliappRepoStep() {
30+
return {
31+
stage ("deploy_cliapp_repo") {
32+
node ("client-test") {
33+
dir("mbed-bootloader-cliapp") {
34+
deleteDir()
35+
execute("git clone --depth 1 [email protected]:ARMmbed/mbed-bootloader-cliapp.git .")
36+
execute("mbed deploy --protocol ssh")
37+
execute("mbed ls")
38+
stash name: "deployed_cliapp_repo", useDefaultExcludes: false, excludes: "**/.git/**"
39+
}
8640
}
8741
}
8842
}
8943
}
9044

91-
/* Jenkins does not allow stages inside parallel execution,
92-
* https://issues.jenkins-ci.org/browse/JENKINS-26107 will solve this by adding labeled blocks
93-
*/
94-
// Actually run the steps in parallel - parallel takes a map as an argument, hence the above.
95-
timestamps {
96-
parallel stepsForParallel
45+
def mbedBootloaderCliStep(step_name,
46+
target,
47+
toolchain,
48+
cliapp_mbed_app,
49+
bootloader_mbed_app,
50+
clitest_testcase_name,
51+
header_offset,
52+
app_offset,
53+
bootloader_repo_name) {
54+
return {
55+
stage (step_name) {
56+
node (toolchain) {
57+
// checkout the bootloader cliapp
58+
dir("mbed-bootloader-cliapp") {
59+
// checkout cliapp source
60+
deleteDir()
61+
unstash "deployed_cliapp_repo"
62+
execute("ls -al")
63+
64+
// checkout and build the bootloader with test config
65+
dir(bootloader_repo_name) {
66+
// checkout bootloader source
67+
deleteDir()
68+
unstash "deployed_bootloader_repo"
69+
execute("mbed config root .")
70+
execute("ls -al")
71+
72+
// build with specified config file
73+
app_config = "configs/test_configs/${bootloader_mbed_app}"
74+
execute("mbed compile -m ${target} -t ${toolchain} -c -v --profile=tiny.json --app-config=${app_config}")
75+
}
76+
77+
// use same version of mbed-os to build cliapp
78+
execute("mv ${bootloader_repo_name}/mbed-os .")
79+
80+
// build cliapp with specified config file
81+
execute("mbed config root .")
82+
execute("mbed test --compile -m ${target} -t ${toolchain} --app-config configs/${cliapp_mbed_app} -n tests-*")
83+
84+
// combine the bootloader with cliapp
85+
bootloader_fn = "${bootloader_repo_name}/BUILD/${target}/${toolchain}/${bootloader_repo_name}.bin"
86+
application_fn = "BUILD/tests/${target}/${toolchain}/TESTS/bootloader/cliapp/cliapp.bin"
87+
test_bin_fn = "testapp.bin"
88+
execute("tools/combine_bootloader_with_app.py -b ${bootloader_fn} -a ${application_fn} " +
89+
"-c ${header_offset} -d ${app_offset} -o ${test_bin_fn} -m ${target}")
90+
91+
// run test with raas hardware
92+
env.RAAS_USERNAME = "ci"
93+
env.RAAS_PASSWORD = "ci"
94+
env.RAAS_PYCLIENT_FORCE_REMOTE_ALLOCATION = 1
95+
env.RAAS_PYCLIENT_ALLOCATION_QUEUE_TIMEOUT = raas_timeout
96+
97+
execute("git clone --depth 1 [email protected]:ARMmbed/mbed-clitest.git")
98+
execute("python mbed-clitest/clitest.py --tc ${clitest_testcase_name} --tcdir TESTS --platform_name ${target} " +
99+
"--type hardware --bin ${test_bin_fn} -v --raas ropi.mbedcloudtesting.com --failure_return_value")
100+
}
101+
}
102+
}
103+
}
97104
}
98105

99-
//Create build steps for parallel execution
100-
def morpheusBuildStep(target,
101-
compilerLabel,
102-
toolchain,
103-
config,
104-
configName,
105-
repoName,
106-
test_filters,
107-
test_dependencies,
108-
mbed_app_json) {
106+
def clitest_configs = [
107+
[ "simple_boot", "K64F", "GCC_ARM", "fake_rot_sd_card.json",
108+
"fake_rot_sd_card.json", "basic_update_test", "0xa400", "0xa000" ],
109+
[ "separate_header_before_app", "K64F", "GCC_ARM", "header_separate.json",
110+
"header_separate_before_app.json", "basic_update_test", "40*1024", "32*1024" ],
111+
[ "separate_header_after_app", "K64F", "GCC_ARM", "header_separate.json",
112+
"header_separate_after_app.json", "basic_update_test", "40*1024", "1020*1024" ]
113+
]
114+
115+
for (int i = 0; i < clitest_configs.size(); i++) {
116+
def test_name = clitest_configs[i][0]
117+
def target = clitest_configs[i][1]
118+
def toolchain = clitest_configs[i][2]
119+
def cliapp_mbed_app = clitest_configs[i][3]
120+
def bootloader_mbed_app = clitest_configs[i][4]
121+
def clitest_testcase_name = clitest_configs[i][5]
122+
def header_offset = clitest_configs[i][6]
123+
def app_offset = clitest_configs[i][7]
124+
def step_name = "${test_name}_${target}_${toolchain}"
125+
stepsForParallel[step_name] = mbedBootloaderCliStep(step_name,
126+
target,
127+
toolchain,
128+
cliapp_mbed_app,
129+
bootloader_mbed_app,
130+
clitest_testcase_name,
131+
header_offset,
132+
app_offset,
133+
repoName)
134+
}
135+
136+
def deployBootloaderRepoStep() {
109137
return {
110-
stage ("${target}_${compilerLabel}_${configName}") {
111-
node ("${compilerLabel}") {
112-
deleteDir()
113-
dir("${repoName}") {
138+
stage ("deploy_bootloader_repo") {
139+
node ("client-test") {
140+
dir(repoName) {
141+
deleteDir()
114142
checkout scm
115-
116-
execute("mbed --version")
117-
execute("mbedhtrun --version")
118143
execute("mbed deploy --protocol ssh")
144+
execute("mbed ls")
145+
stash name: "deployed_bootloader_repo", useDefaultExcludes: false, excludes: "**/.git/**"
146+
}
147+
}
148+
}
149+
}
150+
}
151+
152+
def bootloaderBuildStep(stepName,
153+
target,
154+
toolchain,
155+
repoName,
156+
mbed_app_json) {
157+
return {
158+
stage (stepName) {
159+
node (toolchain) {
160+
dir(repoName) {
161+
// get the deployed source code from previous step
162+
deleteDir()
163+
unstash "deployed_bootloader_repo"
164+
execute("mbed config root .")
165+
execute("ls -al")
119166

120167
// build with default setup
121-
execute("mbed ls")
122-
execute("mbed compile -m ${target} -t ${toolchain} -c -v --profile=tiny.json")
168+
execute("mbed --version")
169+
execute("mbed compile -m ${target} -t ${toolchain} --app-config ${mbed_app_json} -c -v --profile=tiny.json")
170+
}
171+
}
172+
}
173+
}
174+
}
123175

124-
if (toolchain == "ARM" && target == "K64F") {
125-
// setup power cut test dependencies
126-
execute("mbed add https://github.com/ARMmbed/power-cut-jig --protocol ssh")
176+
def build_test_config = [
177+
"K64F": [
178+
"mbed_app.json",
179+
"configs/internal_flash_sotp.json",
180+
"configs/internal_flash_fake_rot.json"],
181+
"NUCLEO_F429ZI": ["mbed_app.json"],
182+
"UBLOX_EVK_ODIN_W2": ["mbed_app.json"],
183+
"NRF52_DK": [
184+
"configs/nrf52_block_device_fake_rot.json",
185+
"configs/nrf52_internal_flash_fake_rot.json"
186+
]
187+
]
127188

128-
// build with test setup
129-
execute("mbed ls")
130-
app_config = "power_cut_test/test_mbed_app.json"
131-
execute("mbed compile -m ${target} -t ${toolchain} -c -v --app-config ${app_config}")
132-
archive "BUILD/${target}/${toolchain}/mbed-bootloader-internal.bin"
189+
for (int i = 0; i < build_test_config.size(); i++) {
190+
for(int j = 0; j < toolchains.size(); j++) {
191+
def target = build_test_config.keySet().asList().get(i)
192+
for (int k = 0; k < build_test_config[target].size(); k++) {
193+
def mbed_app_json = build_test_config[target][k]
194+
def toolchain = toolchains.keySet().asList().get(j)
195+
def stepName = "build_test_${target}_${toolchain}_${mbed_app_json}"
196+
stepsForParallel[stepName] = bootloaderBuildStep(stepName,
197+
target,
198+
toolchain,
199+
repoName,
200+
mbed_app_json)
201+
}
202+
}
203+
}
133204

134-
// Test with power cut hardware
135-
env.RAAS_USERNAME = "ci"
136-
env.RAAS_PASSWORD = "ci"
137-
env.RAAS_PYCLIENT_FORCE_REMOTE_ALLOCATION = 1
205+
def powerCutTestStep(step_name,
206+
target,
207+
toolchain,
208+
repo_name,
209+
app_config,
210+
test_spec) {
211+
return {
212+
stage(step_name) {
213+
node (toolchain) {
214+
dir(repo_name) {
215+
deleteDir()
216+
unstash "deployed_bootloader_repo"
217+
execute("mbed config root .")
218+
execute("ls -al")
138219

139-
test_spec = "power_cut_test/test_spec_armcc.json"
140-
execute("mbedgt --grm ${target}:raas_client:oulab.mbedcloudtesting.com:8055 -V -v --test-spec ${test_spec} -e power_cut_test/host_tests/")
141-
}
220+
// setup power cut test dependencies
221+
execute("mbed add https://github.com/ARMmbed/power-cut-jig --protocol ssh")
222+
223+
// build with test setup
224+
execute("mbed compile -m ${target} -t ${toolchain} -c -v --app-config ${app_config}")
225+
archive "BUILD/${target}/${toolchain}/${repo_name}.bin"
226+
227+
// Test with power cut hardware
228+
env.RAAS_USERNAME = "ci"
229+
env.RAAS_PASSWORD = "ci"
230+
env.RAAS_PYCLIENT_FORCE_REMOTE_ALLOCATION = 1
231+
env.RAAS_PYCLIENT_ALLOCATION_QUEUE_TIMEOUT = raas_timeout
232+
233+
execute("mbedgt --grm ${target}:raas_client:oulab.mbedcloudtesting.com:8055 -V -v " +
234+
"--test-spec ${test_spec} -e power_cut_test/host_tests/")
142235
}
143236
}
144237
}
145238
}
146239
}
240+
241+
def bootloader_test_config = [
242+
["K64F", "ARM", "configs/test_configs/power_cut_test.json", "power_cut_test/test_spec_armcc.json"]
243+
]
244+
245+
for (int i = 0; i < bootloader_test_config.size(); i++) {
246+
def target = bootloader_test_config[i][0]
247+
def toolchain = bootloader_test_config[i][1]
248+
def app_config = bootloader_test_config[i][2]
249+
def test_spec = bootloader_test_config[i][3]
250+
def step_name = "power_cut_test_${target}_${toolchain}"
251+
stepsForParallel[step_name] = powerCutTestStep(step_name,
252+
target,
253+
toolchain,
254+
repoName,
255+
app_config,
256+
test_spec)
257+
}
258+
259+
/* Jenkins does not allow stages inside parallel execution,
260+
* https://issues.jenkins-ci.org/browse/JENKINS-26107 will solve this by adding labeled blocks
261+
*/
262+
// Actually run the steps in parallel - parallel takes a map as an argument, hence the above.
263+
timestamps {
264+
parallel "deploy_bootloader": deployBootloaderRepoStep(), "deploy cliapp": deployCliappRepoStep()
265+
parallel stepsForParallel
266+
}
File renamed without changes.

sotp_fs_config_MbedOS.h renamed to bootloader_pal_user_config.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,9 @@
2525
#define PAL_SIMULATOR_FLASH_OVER_FILE_SYSTEM 0
2626
#define PAL_USE_INTERNAL_FLASH 1
2727
#define PAL_USE_SECURE_TIME 1
28+
#define PAL_THREAD_SAFETY 0
29+
#define Mutex PlatformMutex
30+
#define PAL_INT_FLASH_NUM_SECTIONS 2
2831

2932
#include "mbedOS_default.h"
3033

0 commit comments

Comments
 (0)