mirror of https://github.com/RT-Thread/rt-thread
[action/ci] add qemu-pre-build-and-post-build for RT_SMART build (#10203)
[action/ci] add qemu-pre-build-and-post-build for RT_SMART build
This commit is contained in:
parent
b4e051a890
commit
427e177526
|
@ -69,7 +69,6 @@
|
|||
"RTT_TOOL_CHAIN": "sourcery-arm",
|
||||
"SUB_RTT_BSP": [
|
||||
"phytium/aarch32",
|
||||
"qemu-vexpress-a9",
|
||||
"airm2m/air32f103",
|
||||
"acm32/acm32f0x0-nucleo",
|
||||
"acm32/acm32f0x0-nucleo",
|
||||
|
@ -457,6 +456,14 @@
|
|||
"nrf5x/nrf52840",
|
||||
"nrf5x/nrf5340"
|
||||
]
|
||||
},
|
||||
{
|
||||
"RTT_BSP": "arm-none-bsp-smart",
|
||||
"RTT_TOOL_CHAIN": "sourcery-arm",
|
||||
"RTT_SMART_TOOL_CHAIN": "arm-linux-musleabi",
|
||||
"SUB_RTT_BSP": [
|
||||
"qemu-vexpress-a9"
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
|
|
|
@ -216,6 +216,14 @@ jobs:
|
|||
pip3 install esptool
|
||||
echo "RTT_EXEC_PATH=/opt/riscv32-esp-elf/bin" >> $GITHUB_ENV
|
||||
|
||||
- name: Install Arm Musl ToolChains
|
||||
if: ${{ matrix.legs.RTT_TOOL_CHAIN == 'sourcery-arm' && matrix.legs.RTT_SMART_TOOL_CHAIN == 'arm-linux-musleabi' && success() }}
|
||||
shell: bash
|
||||
run: |
|
||||
wget -q https://github.com/RT-Thread/toolchains-ci/releases/download/v1.7/arm-linux-musleabi_for_x86_64-pc-linux-gnu_stable.tar.bz2
|
||||
sudo tar xjf arm-linux-musleabi_for_x86_64-pc-linux-gnu_stable.tar.bz2 -C /opt
|
||||
/opt/arm-linux-musleabi_for_x86_64-pc-linux-gnu/bin/arm-linux-musleabi-gcc --version
|
||||
|
||||
- name: Install Simulator Tools
|
||||
if: ${{ matrix.legs.RTT_TOOL_CHAIN == 'gcc' && success() }}
|
||||
run: |
|
||||
|
|
|
@ -1,3 +1,14 @@
|
|||
bsp_board_info:
|
||||
arch: arm
|
||||
toolchain: arm-none-eabi-gcc
|
||||
pre_build: |
|
||||
scons --version
|
||||
build_cmd: |
|
||||
scons -j8
|
||||
post_build: |
|
||||
scons --version
|
||||
run_cmd: ./qemu-nographic.sh
|
||||
qemu_flag: true
|
||||
# ------ PERIPHERAL CI ------
|
||||
peripheral.UARTv2:
|
||||
kconfig:
|
||||
|
@ -15,15 +26,39 @@ peripheral.LVGL:
|
|||
- CONFIG_BSP_USING_LVGL=y
|
||||
|
||||
# ------ online-packages CI ------
|
||||
online-packages.tools.coremark:
|
||||
kconfig:
|
||||
- CONFIG_PKG_USING_COREMARK=y
|
||||
- CONFIG_COREMARK_ITERATIONS=36000
|
||||
pre_build: |
|
||||
scons --version
|
||||
build_cmd: |
|
||||
scons -j8
|
||||
post_build: |
|
||||
scons --version
|
||||
ci_build_run_flag : true
|
||||
buildcheckresult: "core_main" #检查编译的log中是否有匹配字
|
||||
msh_cmd: |
|
||||
ps
|
||||
version
|
||||
core_mark
|
||||
msh_cmd_timeout: 60
|
||||
checkresult: 'CoreMark 1.0' #检查执行过程中的log是否有匹配字
|
||||
|
||||
online-packages.misc.entertainment.tetris:
|
||||
kconfig:
|
||||
- CONFIG_PKG_USING_TETRIS=y
|
||||
online-packages.misc.entertainment.2048:
|
||||
kconfig:
|
||||
- CONFIG_PKG_USING_2048=y
|
||||
online-packages.ai.llmchat:
|
||||
# ------ RT_SMART PART ------
|
||||
rt_smart.base:
|
||||
env:
|
||||
RTT_CC_PREFIX: arm-linux-musleabi-
|
||||
RTT_EXEC_PATH: /opt/arm-linux-musleabi_for_x86_64-pc-linux-gnu/bin
|
||||
pre_build: |
|
||||
echo $RTT_CC_PREFIX
|
||||
kconfig:
|
||||
- CONFIG_WEBCLIENT_USING_MBED_TLS=y
|
||||
- CONFIG_BSP_DRV_EMAC=y
|
||||
- CONFIG_PKG_USING_LLMCHAT=y
|
||||
- CONFIG_PKG_LLM_API_KEY="sk-xxxxxx"
|
||||
- CONFIG_RT_USING_SMART=y
|
||||
- CONFIG_RT_USING_MEMHEAP=y
|
||||
- CONFIG_RT_USING_DFS_V2=y
|
||||
|
|
|
@ -1,3 +1,17 @@
|
|||
#
|
||||
# Copyright (c) 2025, RT-Thread Development Team
|
||||
#
|
||||
# SPDX-License-Identifier: Apache-2.0
|
||||
#
|
||||
# Change Logs:
|
||||
# Date Author Notes
|
||||
# 2025-04-21 supperthomas add the smart yml support and add env
|
||||
#
|
||||
import subprocess
|
||||
import threading
|
||||
import time
|
||||
import logging
|
||||
import sys
|
||||
import os
|
||||
import shutil
|
||||
import re
|
||||
|
@ -36,7 +50,7 @@ def run_cmd(cmd, output_info=True):
|
|||
return output_str_list, res
|
||||
|
||||
|
||||
def build_bsp(bsp, scons_args='',name='default'):
|
||||
def build_bsp(bsp, scons_args='',name='default', pre_build_commands=None, post_build_command=None,build_check_result = None,bsp_build_env=None):
|
||||
"""
|
||||
build bsp.
|
||||
|
||||
|
@ -56,21 +70,41 @@ def build_bsp(bsp, scons_args='',name='default'):
|
|||
|
||||
"""
|
||||
success = True
|
||||
# 设置环境变量
|
||||
if bsp_build_env is not None:
|
||||
print("Setting environment variables:")
|
||||
for key, value in bsp_build_env.items():
|
||||
print(f"{key}={value}")
|
||||
os.environ[key] = value # 设置环境变量
|
||||
os.chdir(rtt_root)
|
||||
os.makedirs(f'{rtt_root}/output/bsp/{bsp}', exist_ok=True)
|
||||
if os.path.exists(f"{rtt_root}/bsp/{bsp}/Kconfig"):
|
||||
os.chdir(rtt_root)
|
||||
run_cmd(f'scons -C bsp/{bsp} --pyconfig-silent', output_info=False)
|
||||
run_cmd(f'scons -C bsp/{bsp} --pyconfig-silent', output_info=True)
|
||||
|
||||
os.chdir(f'{rtt_root}/bsp/{bsp}')
|
||||
run_cmd('pkgs --update-force', output_info=False)
|
||||
run_cmd('pkgs --update-force', output_info=True)
|
||||
run_cmd('pkgs --list')
|
||||
|
||||
nproc = multiprocessing.cpu_count()
|
||||
if pre_build_commands is not None:
|
||||
print("Pre-build commands:")
|
||||
print(pre_build_commands)
|
||||
for command in pre_build_commands:
|
||||
print(command)
|
||||
output, returncode = run_cmd(command, output_info=True)
|
||||
print(output)
|
||||
if returncode != 0:
|
||||
print(f"Pre-build command failed: {command}")
|
||||
print(output)
|
||||
os.chdir(rtt_root)
|
||||
# scons 编译命令
|
||||
cmd = f'scons -C bsp/{bsp} -j{nproc} {scons_args}' # --debug=time for debug time
|
||||
__, res = run_cmd(cmd, output_info=True)
|
||||
|
||||
output, res = run_cmd(cmd, output_info=True)
|
||||
if build_check_result is not None:
|
||||
if res != 0 or not check_output(output, build_check_result):
|
||||
print("Build failed or build check result not found")
|
||||
print(output)
|
||||
if res != 0:
|
||||
success = False
|
||||
else:
|
||||
|
@ -83,6 +117,13 @@ def build_bsp(bsp, scons_args='',name='default'):
|
|||
shutil.copy(file, f'{rtt_root}/output/bsp/{bsp}/{name.replace("/", "_")}.{file_type[2:]}')
|
||||
|
||||
os.chdir(f'{rtt_root}/bsp/{bsp}')
|
||||
if post_build_command is not None:
|
||||
for command in post_build_command:
|
||||
output, returncode = run_cmd(command, output_info=True)
|
||||
print(output)
|
||||
if returncode != 0:
|
||||
print(f"Post-build command failed: {command}")
|
||||
print(output)
|
||||
run_cmd('scons -c', output_info=False)
|
||||
|
||||
return success
|
||||
|
@ -158,7 +199,17 @@ def build_bsp_attachconfig(bsp, attach_file):
|
|||
|
||||
return res
|
||||
|
||||
def check_output(output, check_string):
|
||||
"""检查输出中是否包含指定字符串"""
|
||||
output_str = ''.join(output) if isinstance(output, list) else str(output)
|
||||
flag = check_string in output_str
|
||||
if flag == True:
|
||||
print('Success: find string ' + check_string)
|
||||
else:
|
||||
print(output)
|
||||
print(f"::error:: can not find string {check_string} output: {output_str}")
|
||||
|
||||
return flag
|
||||
if __name__ == "__main__":
|
||||
"""
|
||||
build all bsp and attach config.
|
||||
|
@ -169,10 +220,12 @@ if __name__ == "__main__":
|
|||
"""
|
||||
failed = 0
|
||||
count = 0
|
||||
ci_build_run_flag = False
|
||||
qemu_timeout_second = 50
|
||||
|
||||
rtt_root = os.getcwd()
|
||||
srtt_bsp = os.getenv('SRTT_BSP').split(',')
|
||||
|
||||
print(srtt_bsp)
|
||||
for bsp in srtt_bsp:
|
||||
count += 1
|
||||
print(f"::group::Compiling BSP: =={count}=== {bsp} ====")
|
||||
|
@ -207,26 +260,80 @@ if __name__ == "__main__":
|
|||
continue
|
||||
|
||||
config_file = os.path.join(rtt_root, 'bsp', bsp, '.config')
|
||||
|
||||
# 在使用 pre_build_commands 之前,确保它被定义
|
||||
pre_build_commands = None
|
||||
build_command = None
|
||||
post_build_command = None
|
||||
qemu_command = None
|
||||
build_check_result = None
|
||||
commands = None
|
||||
check_result = None
|
||||
bsp_build_env = None
|
||||
for projects in yml_files_content:
|
||||
for name, details in projects.items():
|
||||
# 如果是bsp_board_info,读取基本的信息
|
||||
if(name == 'bsp_board_info'):
|
||||
print(details)
|
||||
pre_build_commands = details.get("pre_build").splitlines()
|
||||
build_command = details.get("build_cmd").splitlines()
|
||||
post_build_command = details.get("post_build").splitlines()
|
||||
qemu_command = details.get("run_cmd")
|
||||
|
||||
if details.get("kconfig") is not None:
|
||||
if details.get("buildcheckresult") is not None:
|
||||
build_check_result = details.get("buildcheckresult")
|
||||
else:
|
||||
build_check_result = None
|
||||
if details.get("msh_cmd") is not None:
|
||||
commands = details.get("msh_cmd").splitlines()
|
||||
else:
|
||||
msh_cmd = None
|
||||
if details.get("checkresult") is not None:
|
||||
check_result = details.get("checkresult")
|
||||
else:
|
||||
check_result = None
|
||||
if details.get("ci_build_run_flag") is not None:
|
||||
ci_build_run_flag = details.get("ci_build_run_flag")
|
||||
else:
|
||||
ci_build_run_flag = None
|
||||
if details.get("pre_build") is not None:
|
||||
pre_build_commands = details.get("pre_build").splitlines()
|
||||
if details.get("env") is not None:
|
||||
bsp_build_env = details.get("env")
|
||||
else:
|
||||
bsp_build_env = None
|
||||
if details.get("build_cmd") is not None:
|
||||
build_command = details.get("build_cmd").splitlines()
|
||||
else:
|
||||
build_command = None
|
||||
if details.get("post_build") is not None:
|
||||
post_build_command = details.get("post_build").splitlines()
|
||||
if details.get("run_cmd") is not None:
|
||||
qemu_command = details.get("run_cmd")
|
||||
else:
|
||||
qemu_command = None
|
||||
count += 1
|
||||
config_bacakup = config_file+'.origin'
|
||||
shutil.copyfile(config_file, config_bacakup)
|
||||
#加载yml中的配置放到.config文件
|
||||
with open(config_file, 'a') as destination:
|
||||
if details.get("kconfig") is None:
|
||||
#如果没有Kconfig,读取下一个配置
|
||||
continue
|
||||
if(projects.get(name) is not None):
|
||||
# 获取Kconfig中所有的信息
|
||||
detail_list=get_details_and_dependencies([name],projects)
|
||||
for line in detail_list:
|
||||
destination.write(line + '\n')
|
||||
scons_arg=[]
|
||||
#如果配置中有scons_arg
|
||||
if details.get('scons_arg') is not None:
|
||||
for line in details.get('scons_arg'):
|
||||
scons_arg.append(line)
|
||||
scons_arg_str=' '.join(scons_arg) if scons_arg else ' '
|
||||
print(f"::group::\tCompiling yml project: =={count}==={name}=scons_arg={scons_arg_str}==")
|
||||
res = build_bsp(bsp, scons_arg_str,name=name)
|
||||
# #开始编译bsp
|
||||
res = build_bsp(bsp, scons_arg_str,name=name,pre_build_commands=pre_build_commands,post_build_command=post_build_command,build_check_result=build_check_result,bsp_build_env =bsp_build_env)
|
||||
if not res:
|
||||
print(f"::error::build {bsp} {name} failed.")
|
||||
add_summary(f'\t- ❌ build {bsp} {name} failed.')
|
||||
|
@ -235,11 +342,15 @@ if __name__ == "__main__":
|
|||
add_summary(f'\t- ✅ build {bsp} {name} success.')
|
||||
print("::endgroup::")
|
||||
|
||||
|
||||
shutil.copyfile(config_bacakup, config_file)
|
||||
os.remove(config_bacakup)
|
||||
|
||||
|
||||
|
||||
attach_dir = os.path.join(rtt_root, 'bsp', bsp, '.ci/attachconfig')
|
||||
attach_list = []
|
||||
#这里是旧的文件方式
|
||||
for root, dirs, files in os.walk(attach_dir):
|
||||
for file in files:
|
||||
if file.endswith('attach'):
|
||||
|
|
Loading…
Reference in New Issue