diff --git a/.github/workflows/bsp_buildings.yml b/.github/workflows/bsp_buildings.yml index 0ea40addcb6..e7ff88ca247 100644 --- a/.github/workflows/bsp_buildings.yml +++ b/.github/workflows/bsp_buildings.yml @@ -34,6 +34,15 @@ on: types: - online-pkgs-static-building-trigger-event workflow_dispatch: + inputs: + output_contral: + description: 'Output Contral' + required: false + default: 'attachconfig' + type: choice + options: + - "attachconfig" + - "versionconfig" permissions: contents: read # to fetch code (actions/checkout) @@ -101,7 +110,6 @@ jobs: runs-on: ubuntu-22.04 needs: generate-matrix name: ${{ matrix.legs.RTT_BSP }} - if: github.repository_owner == 'RT-Thread' strategy: fail-fast: false matrix: ${{ fromJson(needs.generate-matrix.outputs.filtered_matrix) }} @@ -233,13 +241,21 @@ jobs: python tools/ci/bsp_buildings.py - name: Upload output as artifact - if: ${{ success() }} + if: ${{ success() && github.event.inputs.output_contral == 'attachconfig' }} uses: actions/upload-artifact@main with: name: ${{ matrix.legs.RTT_BSP }} if-no-files-found: ignore path: output/ + - name: Upload output as artifact + if: ${{ success() && github.event.inputs.output_contral == 'versionconfig'}} + uses: actions/upload-artifact@main + with: + name: ${{ matrix.legs.RTT_BSP }} + if-no-files-found: ignore + path: version_output/ + - name: Post failure comment if: failure() run: | @@ -247,10 +263,10 @@ jobs: -d '{"body":"@${{ github.actor }}, Thank you for your contribution, but there was an error with the action. Could you please help check the BSP compilation issue? Thank you."}' \ "https://api.github.com/repos/${{ github.repository }}/issues/${{ github.event.pull_request.number }}/comments" # 整合所有的output为一个文件夹 - collect-artifacts: + collect-artifacts1: needs: build runs-on: ubuntu-latest - if: github.event_name != 'pull_request' #排除Pull request + if: ${{github.event_name != 'pull_request' && github.event.inputs.output_contral == 'attachconfig'}} steps: #这里会下载所有产物 - name: Download all artifacts @@ -264,4 +280,21 @@ jobs: uses: actions/upload-artifact@main with: name: 00_all_bsp_output_${{ github.sha }} - path: output/ \ No newline at end of file + path: output/ + collect-artifacts2: + needs: build + runs-on: ubuntu-latest + if: ${{github.event_name != 'pull_request' && github.event.inputs.output_contral == 'versionconfig'}} + steps: + - name: Download all artifacts + uses: actions/download-artifact@main + with: + path: version_output/ + merge-multiple: true + - run: ls -R version_output/ + + - name: Upload combined output as artifact + uses: actions/upload-artifact@main + with: + name: 00_all_bsp_output_${{ github.sha }} + path: version_output/ \ No newline at end of file diff --git a/bsp/stm32/stm32f407-rt-spark/.ci/SConscript b/bsp/stm32/stm32f407-rt-spark/.ci/SConscript new file mode 100644 index 00000000000..ca81e53652d --- /dev/null +++ b/bsp/stm32/stm32f407-rt-spark/.ci/SConscript @@ -0,0 +1,15 @@ +from building import * +import os + +cwd = GetCurrentDir() +src = [] +CPPPATH = [cwd] + +group = DefineGroup('Versionconfig', src, depend = [''], CPPPATH = CPPPATH) + +list = os.listdir(cwd) +for item in list: + if os.path.isfile(os.path.join(cwd, item, 'SConscript')): + group = group + SConscript(os.path.join(item, 'SConscript')) + +Return('group') diff --git a/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/SConscript b/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/SConscript new file mode 100644 index 00000000000..ca81e53652d --- /dev/null +++ b/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/SConscript @@ -0,0 +1,15 @@ +from building import * +import os + +cwd = GetCurrentDir() +src = [] +CPPPATH = [cwd] + +group = DefineGroup('Versionconfig', src, depend = [''], CPPPATH = CPPPATH) + +list = os.listdir(cwd) +for item in list: + if os.path.isfile(os.path.join(cwd, item, 'SConscript')): + group = group + SConscript(os.path.join(item, 'SConscript')) + +Return('group') diff --git a/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/samples/SConscript b/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/samples/SConscript new file mode 100644 index 00000000000..d7834cdf0c5 --- /dev/null +++ b/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/samples/SConscript @@ -0,0 +1,16 @@ +from building import * +import os + +cwd = GetCurrentDir() +src = [] +CPPPATH = [cwd] + +if GetDepend(['VERSIONCONFIG_USING_AHT21_SAMPLE']): + src += ['peripheral_aht21.c'] + +if GetDepend(['VERSIONCONFIG_USING_ICM20608_SAMPLE']): + src += ['peripheral_icm20608.c'] + +group = DefineGroup('Versionconfig', src, depend = [''], CPPPATH = CPPPATH) + +Return('group') diff --git a/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/samples/peripheral_aht21.c b/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/samples/peripheral_aht21.c new file mode 100644 index 00000000000..455f915fa72 --- /dev/null +++ b/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/samples/peripheral_aht21.c @@ -0,0 +1,60 @@ +/* + * Copyright (c) 2006-2024, RT-Thread Development Team + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2024-07-23 Wangyuqiang the first version + * 2024-04-03 Hydevcode + */ + +#include +#include +#include "aht10.h" + +static void aht10_entry(void *parameter) +{ + float humidity, temperature; + aht10_device_t dev; + + const char *i2c_bus_name = "i2c3"; + int count = 0; + + rt_thread_mdelay(2000); + + dev = aht10_init(i2c_bus_name); + if (dev == RT_NULL) + { + rt_kprintf("The sensor initializes failure"); + } + + rt_kprintf("AHT10 has been initialized!"); + + while (1) + { + humidity = aht10_read_humidity(dev); + rt_kprintf("Humidity : %d.%d %%", (int)humidity, (int)(humidity * 10) % 10); + + temperature = aht10_read_temperature(dev); + rt_kprintf("Temperature: %d.%d", (int)temperature, (int)(temperature * 10) % 10); + + rt_thread_mdelay(1000); + } + +} + +int aht10_thread_port(void) +{ + rt_thread_t res = rt_thread_create("aht10", aht10_entry, RT_NULL, 1024, 20, 50); + if(res == RT_NULL) + { + rt_kprintf("aht10 thread create failed!"); + return -RT_ERROR; + } + + rt_thread_startup(res); + + return RT_EOK; +} +INIT_DEVICE_EXPORT(aht10_thread_port); \ No newline at end of file diff --git a/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/samples/peripheral_icm20608.c b/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/samples/peripheral_icm20608.c new file mode 100644 index 00000000000..804c74a7ef4 --- /dev/null +++ b/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/samples/peripheral_icm20608.c @@ -0,0 +1,63 @@ +/* + * Copyright (c) 2006-2024, RT-Thread Development Team + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2024-04-03 Hydevcode the first version + */ + +#include +#include +#include "icm20608.h" + +static void icm20608_entry(void *parameter) +{ + icm20608_device_t dev = RT_NULL; + rt_int16_t x, y, z; + rt_uint32_t i; + + const char *i2c_bus_name = "i2c2"; + int count = 0; + + rt_thread_mdelay(2000); + + dev = icm20608_init(i2c_bus_name); + if (dev == RT_NULL) + { + rt_kprintf("The sensor initializes failure"); + } + + rt_kprintf("ICM20608 has been initialized!"); + + while (1) + { + /* read the sensor digital output */ + icm20608_get_accel(dev, &x, &y, &z); + + rt_kprintf("accelerometer: X%6d Y%6d Z%6d\n", x, y, z); + + icm20608_get_gyro(dev, &x, &y, &z); + + rt_kprintf("gyroscope : X%6d Y%6d Z%6d\n", x, y, z); + + rt_thread_mdelay(1000); + } + +} + +int icm20608_thread_port(void) +{ + rt_thread_t res = rt_thread_create("icm20608", icm20608_entry, RT_NULL, 1024, 20, 50); + if(res == RT_NULL) + { + rt_kprintf("icm20608 thread create failed!"); + return -RT_ERROR; + } + + rt_thread_startup(res); + + return RT_EOK; +} +INIT_DEVICE_EXPORT(icm20608_thread_port); \ No newline at end of file diff --git a/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/versionconfig.yml b/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/versionconfig.yml new file mode 100644 index 00000000000..23a540fb699 --- /dev/null +++ b/bsp/stm32/stm32f407-rt-spark/.ci/versionconfig/versionconfig.yml @@ -0,0 +1,12 @@ +scons.args: &scons + scons_arg: + - '--strict' +# ------ peripheral CI ------ +peripheral.aht21: + kconfig: + - CONFIG_BSP_USING_AHT21=y + - CONFIG_VERSIONCONFIG_USING_AHT21_SAMPLE=y +peripheral.icm20608: + kconfig: + - CONFIG_BSP_USING_ICM20608=y + - CONFIG_VERSIONCONFIG_USING_ICM20608_SAMPLE=y \ No newline at end of file diff --git a/bsp/stm32/stm32f407-rt-spark/board/SConscript b/bsp/stm32/stm32f407-rt-spark/board/SConscript index cfb071f000d..fc3f788144d 100644 --- a/bsp/stm32/stm32f407-rt-spark/board/SConscript +++ b/bsp/stm32/stm32f407-rt-spark/board/SConscript @@ -1,6 +1,5 @@ import os from building import * - cwd = GetCurrentDir() # add general drivers @@ -11,8 +10,8 @@ CubeMX_Config/Src/stm32f4xx_hal_msp.c path = [cwd] path += [os.path.join(cwd, 'CubeMX_Config', 'Inc')] -CPPDEFINES = ['STM32F407xx'] -group = DefineGroup('Drivers', src, depend = [''], CPPPATH = path, CPPDEFINES = CPPDEFINES) + +group = DefineGroup('Drivers', src, depend = [''], CPPPATH = path) # if os.path.isfile(os.path.join(cwd, "ports", 'SConscript')): # group = group + SConscript(os.path.join("ports", 'SConscript')) diff --git a/tools/ci/bsp_buildings.py b/tools/ci/bsp_buildings.py index 8ba412a779d..1680b786d39 100644 --- a/tools/ci/bsp_buildings.py +++ b/tools/ci/bsp_buildings.py @@ -141,8 +141,8 @@ def build_bsp_attachconfig(bsp, attach_file): """ config_file = os.path.join(rtt_root, 'bsp', bsp, '.config') - config_bacakup = config_file+'.origin' - shutil.copyfile(config_file, config_bacakup) + config_backup = config_file+'.origin' + shutil.copyfile(config_file, config_backup) attachconfig_dir = os.path.join(rtt_root, 'bsp', bsp, '.ci/attachconfig') attach_path = os.path.join(attachconfig_dir, attach_file) @@ -153,11 +153,44 @@ def build_bsp_attachconfig(bsp, attach_file): res = build_bsp(bsp, scons_args,name=attach_file) - shutil.copyfile(config_bacakup, config_file) - os.remove(config_bacakup) + shutil.copyfile(config_backup, config_file) + os.remove(config_backup) return res +def build_bsp_versionconfig(bsp, scons_args='',name='default'): + success = True + os.chdir(rtt_root) + os.makedirs(f'{rtt_root}/version_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) + + os.chdir(f'{rtt_root}/bsp/{bsp}') + + run_cmd('pkgs --update-force', output_info=False) + run_cmd('pkgs --list') + + nproc = multiprocessing.cpu_count() + os.chdir(rtt_root) + cmd = f'scons -C bsp/{bsp} -j{nproc} {scons_args}' # --debug=time for debug time + __, res = run_cmd(cmd, output_info=True) + + if res != 0: + success = False + else: + #拷贝当前的文件夹下面的所有以elf结尾的文件拷贝到rt-thread/output文件夹下 + import glob + # 拷贝编译生成的文件到output目录,文件拓展为 elf,bin,hex + for file_type in ['*.elf', '*.bin', '*.hex']: + files = glob.glob(f'{rtt_root}/bsp/{bsp}/{file_type}') + for file in files: + shutil.copy(file, f'{rtt_root}/version_output/bsp/{bsp}/{name.replace("/", "_")}.{file_type[2:]}') + + os.chdir(f'{rtt_root}/bsp/{bsp}') + run_cmd('scons -c', output_info=False) + + return success if __name__ == "__main__": """ @@ -211,8 +244,8 @@ def build_bsp_attachconfig(bsp, attach_file): for projects in yml_files_content: for name, details in projects.items(): count += 1 - config_bacakup = config_file+'.origin' - shutil.copyfile(config_file, config_bacakup) + config_backup = config_file+'.origin' + shutil.copyfile(config_file, config_backup) with open(config_file, 'a') as destination: if details.get("kconfig") is None: continue @@ -235,8 +268,106 @@ def build_bsp_attachconfig(bsp, attach_file): add_summary(f'\t- ✅ build {bsp} {name} success.') print("::endgroup::") - shutil.copyfile(config_bacakup, config_file) - os.remove(config_bacakup) + shutil.copyfile(config_backup, config_file) + os.remove(config_backup) + version_yml_files_content = [] + directory = os.path.join(rtt_root, 'bsp', bsp, '.ci/versionconfig') + if os.path.exists(directory): + for root, dirs, files in os.walk(directory): + for filename in files: + if filename.endswith('versionconfig.yml'): + file_path = os.path.join(root, filename) + if os.path.exists(file_path): + try: + with open(file_path, 'r') as file: + content = yaml.safe_load(file) + if content is None: + continue + version_yml_files_content.append(content) + except yaml.YAMLError as e: + print(f"::error::Error parsing YAML file: {e}") + continue + except Exception as e: + print(f"::error::Error reading file: {e}") + continue + + config_file = os.path.join(rtt_root, 'bsp', bsp, '.config') + rtconfig_file = os.path.join(rtt_root, 'bsp', bsp, 'rtconfig.h') + for projects in version_yml_files_content: + for name, details in projects.items(): + detail_list=[] + count += 1 + config_backup = config_file+'.origin' + shutil.copyfile(config_file, config_backup) + with open(config_file, 'a') as destination: + if details.get("kconfig") is None: + continue + if(projects.get(name) is not None): + detail_list=get_details_and_dependencies([name],projects) + for line in detail_list: + destination.write(line + '\n') + # 判断前缀是否有version + 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 version yml project: =={count}==={name}=scons_arg={scons_arg_str}==") + success = True + os.chdir(rtt_root) + os.makedirs(f'{rtt_root}/version_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) + + os.chdir(f'{rtt_root}/bsp/{bsp}') + + run_cmd('pkgs --update-force', output_info=False) + pattern = r'VERSIONCONFIG_[A-Z0-9_]+' + with open(rtconfig_file, 'a') as destination: + for line in detail_list: + match = re.search(pattern, line) + if match: + # 提取匹配到的部分 + extracted_part = match.group(0) + # 组合成 #define 格式 + result = f"#define {extracted_part}" + destination.write(result + '\n') + print(result) + else: + continue + + run_cmd('pkgs --list') + + nproc = multiprocessing.cpu_count() + os.chdir(rtt_root) + cmd = f'scons -C bsp/{bsp} -j{nproc} {scons_arg_str}' # --debug=time for debug time + __, res = run_cmd(cmd, output_info=True) + + if res != 0: + success = False + else: + #拷贝当前的文件夹下面的所有以elf结尾的文件拷贝到rt-thread/output文件夹下 + import glob + # 拷贝编译生成的文件到output目录,文件拓展为 elf,bin,hex + for file_type in ['*.elf', '*.bin', '*.hex']: + files = glob.glob(f'{rtt_root}/bsp/{bsp}/{file_type}') + for file in files: + shutil.copy(file, f'{rtt_root}/version_output/bsp/{bsp}/{name.replace("/", "_")}.{file_type[2:]}') + + os.chdir(f'{rtt_root}/bsp/{bsp}') + run_cmd('scons -c', output_info=False) + res=success + if not res: + print(f"::error::build {bsp} {name} failed.") + add_summary(f'\t- ❌ build {bsp} {name} failed.') + failed += 1 + else: + add_summary(f'\t- ✅ build {bsp} {name} success.') + print("::endgroup::") + + shutil.copyfile(config_backup, config_file) + os.remove(config_backup) attach_dir = os.path.join(rtt_root, 'bsp', bsp, '.ci/attachconfig') attach_list = []