From 14d44171b59fc273adcccc1464da6e6cfb2c1864 Mon Sep 17 00:00:00 2001 From: hathach Date: Thu, 25 Jan 2024 19:13:11 +0700 Subject: bump up to actions/setup-python@v5 --- .github/workflows/pre-commit.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to '.github/workflows/pre-commit.yml') diff --git a/.github/workflows/pre-commit.yml b/.github/workflows/pre-commit.yml index 2e9ae9264..e36259daa 100644 --- a/.github/workflows/pre-commit.yml +++ b/.github/workflows/pre-commit.yml @@ -15,7 +15,7 @@ jobs: runs-on: ubuntu-latest steps: - name: Setup Python - uses: actions/setup-python@v4 + uses: actions/setup-python@v5 with: python-version: '3.x' -- cgit v1.3.1 From ba6babf570752a28379aab51d9c27e7b9efe872d Mon Sep 17 00:00:00 2001 From: Ha Thach Date: Thu, 9 May 2024 20:43:46 +0700 Subject: Rework ci (#2631) * add name field to usbd_class_driver_t * ci: use set matrix py script * add riscv32 and cmake support for ch32v307, fomu, gd32vf103 * update build_cmake.py to take --family --board --toolchain * separate hil test to its own workflow * move esp32 board into separated hil json * add make build to ci * remov build_make.py * build.py support esp32 board * setup toolchain support esp-idf * fix missing click * merge family in matrix build to reduce jobs * skip cifuzz since it still has issue with get_deps and click --- .github/actions/prepare_build/action.yml | 30 +++ .github/actions/setup_toolchain/action.yml | 31 +++ .../actions/setup_toolchain/download/action.yml | 29 ++ .github/workflows/build_aarch64.yml | 70 ----- .github/workflows/build_arm.yml | 57 ---- .github/workflows/build_cmake.yml | 295 ++++----------------- .github/workflows/build_esp.yml | 19 +- .github/workflows/build_family.yml | 64 +++++ .github/workflows/build_iar.yml | 4 +- .github/workflows/build_renesas.yml | 6 +- .github/workflows/build_riscv.yml | 71 ----- .github/workflows/build_win_mac.yml | 6 +- .github/workflows/ci_set_matrix.py | 51 ++++ .github/workflows/cifuzz.yml | 3 + .github/workflows/codeql-buildscript.sh | 3 +- .github/workflows/hil_test.yml | 125 +++++++++ .github/workflows/pre-commit.yml | 1 + .idea/cmake.xml | 8 +- examples/build_system/cmake/cpu/rv32i-ilp32.cmake | 19 ++ .../build_system/cmake/cpu/rv32imac-ilp32.cmake | 18 ++ .../build_system/cmake/toolchain/riscv_gcc.cmake | 21 ++ examples/build_system/make/cpu/rv32i-ilp32.mk | 13 + examples/build_system/make/cpu/rv32imac-ilp32.mk | 13 + examples/build_system/make/toolchain/riscv_gcc.mk | 20 ++ examples/device/video_capture/skip.txt | 1 - .../ch32v307/boards/ch32v307v_r1_1v0/board.cmake | 4 + .../ch32v307/boards/ch32v307v_r1_1v0/debug_uart.c | 110 -------- .../ch32v307/boards/ch32v307v_r1_1v0/debug_uart.h | 31 --- hw/bsp/ch32v307/debug_uart.c | 110 ++++++++ hw/bsp/ch32v307/debug_uart.h | 31 +++ hw/bsp/ch32v307/family.cmake | 114 ++++++++ hw/bsp/ch32v307/family.mk | 12 +- .../led_strip_rmt_ws2812/dependencies.lock | 15 -- hw/bsp/family_support.cmake | 24 +- hw/bsp/fomu/boards/fomu/board.cmake | 4 + hw/bsp/fomu/family.c | 121 +++++++++ hw/bsp/fomu/family.cmake | 91 +++++++ hw/bsp/fomu/family.mk | 9 +- hw/bsp/fomu/fomu.c | 120 --------- .../boards/sipeed_longan_nano/board.cmake | 13 + .../gd32vf103/boards/sipeed_longan_nano/board.mk | 1 - hw/bsp/gd32vf103/family.c | 4 +- hw/bsp/gd32vf103/family.cmake | 119 +++++++++ hw/bsp/gd32vf103/family.mk | 10 +- hw/bsp/lpc51/family.cmake | 1 - src/device/usbd.c | 28 +- src/device/usbd_pvt.h | 7 +- test/hil/hfp.json | 25 ++ test/hil/hil_hfp.json | 25 -- test/hil/hil_pi4.json | 37 --- test/hil/hil_test.py | 69 +++-- test/hil/pi4.json | 27 ++ test/hil/pi4_esp32.json | 14 + tools/build.py | 177 +++++++++++++ tools/build_board.py | 69 ----- tools/build_cmake.py | 105 -------- tools/build_make.py | 80 ------ tools/get_deps.py | 54 ++-- 58 files changed, 1482 insertions(+), 1157 deletions(-) create mode 100644 .github/actions/prepare_build/action.yml create mode 100644 .github/actions/setup_toolchain/action.yml create mode 100644 .github/actions/setup_toolchain/download/action.yml delete mode 100644 .github/workflows/build_aarch64.yml delete mode 100644 .github/workflows/build_arm.yml create mode 100644 .github/workflows/build_family.yml delete mode 100644 .github/workflows/build_riscv.yml create mode 100644 .github/workflows/ci_set_matrix.py create mode 100644 .github/workflows/hil_test.yml create mode 100644 examples/build_system/cmake/cpu/rv32i-ilp32.cmake create mode 100644 examples/build_system/cmake/cpu/rv32imac-ilp32.cmake create mode 100644 examples/build_system/cmake/toolchain/riscv_gcc.cmake create mode 100644 examples/build_system/make/cpu/rv32i-ilp32.mk create mode 100644 examples/build_system/make/cpu/rv32imac-ilp32.mk create mode 100644 examples/build_system/make/toolchain/riscv_gcc.mk create mode 100644 hw/bsp/ch32v307/boards/ch32v307v_r1_1v0/board.cmake delete mode 100644 hw/bsp/ch32v307/boards/ch32v307v_r1_1v0/debug_uart.c delete mode 100644 hw/bsp/ch32v307/boards/ch32v307v_r1_1v0/debug_uart.h create mode 100644 hw/bsp/ch32v307/debug_uart.c create mode 100644 hw/bsp/ch32v307/debug_uart.h create mode 100644 hw/bsp/ch32v307/family.cmake delete mode 100644 hw/bsp/espressif/components/led_strip/examples/led_strip_rmt_ws2812/dependencies.lock create mode 100644 hw/bsp/fomu/boards/fomu/board.cmake create mode 100644 hw/bsp/fomu/family.c create mode 100644 hw/bsp/fomu/family.cmake delete mode 100644 hw/bsp/fomu/fomu.c create mode 100644 hw/bsp/gd32vf103/boards/sipeed_longan_nano/board.cmake create mode 100644 hw/bsp/gd32vf103/family.cmake create mode 100644 test/hil/hfp.json delete mode 100644 test/hil/hil_hfp.json delete mode 100644 test/hil/hil_pi4.json create mode 100644 test/hil/pi4.json create mode 100644 test/hil/pi4_esp32.json create mode 100644 tools/build.py delete mode 100644 tools/build_board.py delete mode 100644 tools/build_cmake.py delete mode 100644 tools/build_make.py (limited to '.github/workflows/pre-commit.yml') diff --git a/.github/actions/prepare_build/action.yml b/.github/actions/prepare_build/action.yml new file mode 100644 index 000000000..5f2c544c1 --- /dev/null +++ b/.github/actions/prepare_build/action.yml @@ -0,0 +1,30 @@ +name: Prepare to build + +inputs: + family: + required: true + type: string + +runs: + using: "composite" + steps: + - name: Setup Python + uses: actions/setup-python@v5 + with: + python-version: '3.x' + + - name: Checkout pico-sdk for rp2040 + if: contains(inputs.family, 'rp2040') + uses: actions/checkout@v4 + with: + repository: raspberrypi/pico-sdk + ref: develop + path: pico-sdk + + - name: Get Dependencies + run: | + sudo apt install -y ninja-build + pip install click + python3 tools/get_deps.py ${{ inputs.family }} + echo >> $GITHUB_ENV "PICO_SDK_PATH=$GITHUB_WORKSPACE/pico-sdk" + shell: bash diff --git a/.github/actions/setup_toolchain/action.yml b/.github/actions/setup_toolchain/action.yml new file mode 100644 index 000000000..b59ece116 --- /dev/null +++ b/.github/actions/setup_toolchain/action.yml @@ -0,0 +1,31 @@ +name: Setup Toolchain + +inputs: + toolchain: + required: true + type: string + toolchain_url: + required: false + type: string + +runs: + using: "composite" + steps: + - name: Install ARM GCC + if: inputs.toolchain == 'arm-gcc' + uses: carlosperate/arm-none-eabi-gcc-action@v1 + with: + release: '12.3.Rel1' + + - name: Pull ESP-IDF docker + if: inputs.toolchain == 'esp-idf' + run: docker pull espressif/idf:latest + shell: bash + + - name: Download Toolchain + if: >- + inputs.toolchain != 'arm-gcc' && + inputs.toolchain != 'esp-idf' + uses: ./.github/actions/setup_toolchain/download + with: + toolchain_url: ${{ inputs.toolchain_url }} diff --git a/.github/actions/setup_toolchain/download/action.yml b/.github/actions/setup_toolchain/download/action.yml new file mode 100644 index 000000000..db85e9027 --- /dev/null +++ b/.github/actions/setup_toolchain/download/action.yml @@ -0,0 +1,29 @@ +name: Download Toolchain + +inputs: + toolchain_url: + required: true + type: string + +runs: + using: "composite" + steps: + - name: Cache Toolchain + uses: actions/cache@v4 + id: cache-toolchain + with: + path: ~/cache/toolchain + key: ${{ runner.os }}-${{ inputs.toolchain_url }} + + - name: Install Toolchain + if: steps.cache-toolchain.outputs.cache-hit != 'true' + run: | + mkdir -p ~/cache/toolchain + wget --progress=dot:mega ${{ inputs.toolchain_url }} -O toolchain.tar.gz + tar -C ~/cache/toolchain -xaf toolchain.tar.gz + shell: bash + + - name: Set Toolchain Path + run: | + echo >> $GITHUB_PATH `echo ~/cache/toolchain/*/bin` + shell: bash diff --git a/.github/workflows/build_aarch64.yml b/.github/workflows/build_aarch64.yml deleted file mode 100644 index 237692498..000000000 --- a/.github/workflows/build_aarch64.yml +++ /dev/null @@ -1,70 +0,0 @@ -name: Build AArch64 - -on: - workflow_dispatch: - push: - paths: - - 'src/**' - - 'examples/**' - - 'lib/**' - - 'hw/**' - - '.github/workflows/build_aarch64.yml' - pull_request: - branches: [ master ] - paths: - - 'src/**' - - 'examples/**' - - 'lib/**' - - 'hw/**' - - '.github/workflows/build_aarch64.yml' - -concurrency: - group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} - cancel-in-progress: true - -jobs: - # --------------------------------------- - # Build AARCH64 family - # --------------------------------------- - build-arm: - runs-on: ubuntu-latest - strategy: - fail-fast: false - matrix: - family: - # Alphabetical order - - 'broadcom_64bit' - steps: - - name: Setup Python - uses: actions/setup-python@v5 - with: - python-version: '3.x' - - - name: Checkout TinyUSB - uses: actions/checkout@v4 - - - name: Set Toolchain URL - run: echo >> $GITHUB_ENV TOOLCHAIN_URL=https://developer.arm.com/-/media/Files/downloads/gnu-a/10.3-2021.07/binrel/gcc-arm-10.3-2021.07-x86_64-aarch64-none-elf.tar.xz - - - name: Cache Toolchain - uses: actions/cache@v4 - id: cache-toolchain - with: - path: ~/cache/ - key: ${{ runner.os }}-21-11-02-${{ env.TOOLCHAIN_URL }} - - - name: Install Toolchain - if: steps.cache-toolchain.outputs.cache-hit != 'true' - run: | - mkdir -p ~/cache/toolchain - wget --progress=dot:mega $TOOLCHAIN_URL -O toolchain.tar.gz - tar -C ~/cache/toolchain -xaf toolchain.tar.gz - - - name: Set Toolchain Path - run: echo >> $GITHUB_PATH `echo ~/cache/toolchain/*/bin` - - - name: Get Dependencies - run: python3 tools/get_deps.py ${{ matrix.family }} - - - name: Build - run: python3 tools/build_make.py ${{ matrix.family }} diff --git a/.github/workflows/build_arm.yml b/.github/workflows/build_arm.yml deleted file mode 100644 index 14c6d519c..000000000 --- a/.github/workflows/build_arm.yml +++ /dev/null @@ -1,57 +0,0 @@ -name: Build ARM - -on: - workflow_dispatch: - push: - paths: - - 'src/**' - - 'examples/**' - - 'lib/**' - - 'hw/**' - - 'tools/get_deps.py' - - '.github/workflows/build_arm.yml' - pull_request: - branches: [ master ] - paths: - - 'src/**' - - 'examples/**' - - 'lib/**' - - 'hw/**' - - 'tools/get_deps.py' - - '.github/workflows/build_arm.yml' - -concurrency: - group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} - cancel-in-progress: true - -jobs: - # --------------------------------------- - # Build ARM family - # --------------------------------------- - build-arm: - runs-on: ubuntu-latest - strategy: - fail-fast: false - matrix: - family: - # Alphabetical order - - 'mm32' - steps: - - name: Setup Python - uses: actions/setup-python@v5 - with: - python-version: '3.x' - - - name: Install ARM GCC - uses: carlosperate/arm-none-eabi-gcc-action@v1 - with: - release: '11.2-2022.02' - - - name: Checkout TinyUSB - uses: actions/checkout@v4 - - - name: Get Dependencies - run: python3 tools/get_deps.py ${{ matrix.family }} - - - name: Build - run: python3 tools/build_make.py ${{ matrix.family }} diff --git a/.github/workflows/build_cmake.yml b/.github/workflows/build_cmake.yml index c1f85ad9c..b62a0e9bd 100644 --- a/.github/workflows/build_cmake.yml +++ b/.github/workflows/build_cmake.yml @@ -1,4 +1,4 @@ -name: Build CMake +name: Build on: workflow_dispatch: @@ -8,9 +8,11 @@ on: - 'examples/**' - 'lib/**' - 'hw/**' - - 'test/hil/**' - 'tools/get_deps.py' + - 'tools/build.py' + - '.github/actions/**' - '.github/workflows/build_cmake.yml' + - '.github/workflows/ci_set_matrix.py' pull_request: branches: [ master ] paths: @@ -18,141 +20,20 @@ on: - 'examples/**' - 'lib/**' - 'hw/**' - - 'test/hil/**' - 'tools/get_deps.py' + - 'tools/build.py' + - '.github/actions/**' - '.github/workflows/build_cmake.yml' - + - '.github/workflows/ci_set_matrix.py' concurrency: group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} cancel-in-progress: true jobs: - # --------------------------------------- - # Build ARM with GCC - # --------------------------------------- - arm-gcc: - runs-on: ubuntu-latest - strategy: - fail-fast: false - matrix: - family: - # Alphabetical order - - 'broadcom_32bit' - - 'imxrt' - - 'kinetis_k kinetis_kl kinetis_k32l2' - - 'lpc11 lpc13 lpc15' - - 'lpc17 lpc18 lpc40 lpc43' - - 'lpc51 lpc54 lpc55' - - 'mcx' - - 'msp432e4' - - 'mm32' - - 'nrf' - - 'ra' - - 'rp2040' - - 'samd11 samd21 saml2x samd5x_e5x samg' - - 'stm32f0' - - 'stm32f1' - - 'stm32f2' - - 'stm32f3' - - 'stm32f4' - - 'stm32f7' - - 'stm32g0' - - 'stm32g4' - - 'stm32h5' - - 'stm32h7' - - 'stm32l4' - - 'stm32u5' - - 'stm32wb' - - 'tm4c' - - 'xmc4000' - steps: - - name: Setup Python - uses: actions/setup-python@v5 - with: - python-version: '3.x' - - - name: Install ARM GCC - uses: carlosperate/arm-none-eabi-gcc-action@v1 - with: - release: '12.3.Rel1' - - - name: Checkout TinyUSB - uses: actions/checkout@v4 - - - name: Checkout pico-sdk for rp2040 - if: matrix.family == 'rp2040' - uses: actions/checkout@v4 - with: - repository: raspberrypi/pico-sdk - ref: develop - path: pico-sdk - - - name: Get Dependencies - run: | - sudo apt install -y ninja-build - python3 tools/get_deps.py ${{ matrix.family }} - - - name: Build - run: python tools/build_cmake.py ${{ matrix.family }} - env: - PICO_SDK_PATH: ${{ github.workspace }}/pico-sdk - - - name: Upload Artifacts for Hardware Testing (rp2040) - if: contains(matrix.family, 'rp2040') && github.repository_owner == 'hathach' - uses: actions/upload-artifact@v4 - with: - name: raspberry_pi_pico - path: | - cmake-build/cmake-build-raspberry_pi_pico/*/*/*.elf - - - name: Upload Artifacts for Hardware Testing (nRF) - if: contains(matrix.family, 'nrf') && github.repository_owner == 'hathach' - uses: actions/upload-artifact@v4 - with: - name: feather_nrf52840_express - path: | - cmake-build/cmake-build-feather_nrf52840_express/*/*/*.elf - - - name: Upload Artifacts for Hardware Testing (samd51) - if: contains(matrix.family, 'samd5x_e5x') && github.repository_owner == 'hathach' - uses: actions/upload-artifact@v4 - with: - name: itsybitsy_m4 - path: | - cmake-build/cmake-build-itsybitsy_m4/*/*/*.bin - - # --------------------------------------- - # Build ARM with Clang - # --------------------------------------- - arm-clang: + set-matrix: runs-on: ubuntu-latest - strategy: - fail-fast: false - matrix: - family: - # Alphabetical order - - 'imxrt' - - 'kinetis_k kinetis_kl' - - 'lpc17 lpc18 lpc40 lpc43' - - 'lpc54 lpc55' - #- 'mcx' not working with gcc anymore, need to fix this first - - 'nrf' - #- 'ra' port later - #- 'rp2040' port later - - 'samd21' - - 'samd5x_e5x' - - 'stm32f0' - - 'stm32f1' - - 'stm32f2' - - 'stm32f3' - - 'stm32f4' - - 'stm32f7' - - 'stm32g0' - - 'stm32g4' - - 'stm32h5' - - 'stm32h7' - - 'stm32l4' - - 'stm32u5' + outputs: + json: ${{ steps.set-matrix-json.outputs.matrix }} steps: - name: Setup Python uses: actions/setup-python@v5 @@ -162,137 +43,51 @@ jobs: - name: Checkout TinyUSB uses: actions/checkout@v4 - - name: Checkout pico-sdk for rp2040 - if: matrix.family == 'rp2040' - uses: actions/checkout@v4 - with: - repository: raspberrypi/pico-sdk - ref: develop - path: pico-sdk - - - name: Set Toolchain URL - run: echo >> $GITHUB_ENV TOOLCHAIN_URL=https://github.com/ARM-software/LLVM-embedded-toolchain-for-Arm/releases/download/release-17.0.1/LLVMEmbeddedToolchainForArm-17.0.1-Linux-x86_64.tar.xz - - - name: Cache Toolchain - uses: actions/cache@v4 - id: cache-toolchain - with: - path: ~/cache/ - key: ${{ runner.os }}-24-04-17-${{ env.TOOLCHAIN_URL }} - - - name: Install Toolchain - if: steps.cache-toolchain.outputs.cache-hit != 'true' - run: | - mkdir -p ~/cache/toolchain - wget --progress=dot:mega $TOOLCHAIN_URL -O toolchain.tar.xz - tar -C ~/cache/toolchain -xaf toolchain.tar.xz - - - name: Prepare to build + - name: Generate matrix json + id: set-matrix-json run: | - echo >> $GITHUB_PATH `echo ~/cache/toolchain/*/bin` - sudo apt install -y ninja-build - python3 tools/get_deps.py ${{ matrix.family }} - - - name: Build - run: python tools/build_cmake.py ${{ matrix.family }} -DTOOLCHAIN=clang - env: - PICO_SDK_PATH: ${{ github.workspace }}/pico-sdk + MATRIX_JSON=$(python .github/workflows/ci_set_matrix.py) + echo "matrix=$MATRIX_JSON" + echo "matrix=$MATRIX_JSON" >> $GITHUB_OUTPUT # --------------------------------------- - # Build MSP430 with GCC + # Build CMake # --------------------------------------- - msp430-gcc: - runs-on: ubuntu-latest + cmake: + needs: set-matrix + uses: ./.github/workflows/build_family.yml strategy: fail-fast: false matrix: - family: - # Alphabetical order - - 'msp430' - steps: - - name: Setup Python - uses: actions/setup-python@v5 - with: - python-version: '3.x' - - - name: Checkout TinyUSB - uses: actions/checkout@v4 - - - name: Set Toolchain URL - run: echo >> $GITHUB_ENV TOOLCHAIN_URL=http://software-dl.ti.com/msp430/msp430_public_sw/mcu/msp430/MSPGCC/9_2_0_0/export/msp430-gcc-9.2.0.50_linux64.tar.bz2 - - - name: Cache Toolchain - uses: actions/cache@v4 - id: cache-toolchain - with: - path: ~/cache/ - key: ${{ runner.os }}-24-04-17-${{ env.TOOLCHAIN_URL }} - - - name: Install Toolchain - if: steps.cache-toolchain.outputs.cache-hit != 'true' - run: | - mkdir -p ~/cache/toolchain - wget --progress=dot:mega $TOOLCHAIN_URL -O toolchain.tar.bz2 - tar -C ~/cache/toolchain -xaf toolchain.tar.bz2 - - - name: Prepare to build - run: | - echo >> $GITHUB_PATH `echo ~/cache/toolchain/*/bin` - sudo apt install -y ninja-build - python3 tools/get_deps.py ${{ matrix.family }} - - - name: Build - run: python tools/build_cmake.py ${{ matrix.family }} + toolchain: + - 'aarch64-gcc' + - 'arm-clang' + - 'arm-gcc' + - 'msp430-gcc' + - 'riscv-gcc' + with: + build-system: 'cmake' + toolchain: ${{ matrix.toolchain }} + toolchain_url: ${{ fromJSON(needs.set-matrix.outputs.json)[matrix.toolchain].toolchain_url }} + build-family: ${{ toJSON(fromJSON(needs.set-matrix.outputs.json)[matrix.toolchain].family) }} # --------------------------------------- - # Hardware in the loop (HIL) - # Current self-hosted instance is running on an RPI4. For attached hardware checkout hil_pi4.json + # Build Make # --------------------------------------- - hil-test: - # run only with hathach's commit due to limited resource on RPI4 - if: github.repository_owner == 'hathach' - needs: arm-gcc - runs-on: [self-hosted, rp2040, nrf52840, hardware-in-the-loop] + make: + needs: set-matrix + uses: ./.github/workflows/build_family.yml strategy: fail-fast: false matrix: - board: - - 'feather_nrf52840_express' - - 'itsybitsy_m4' - - 'raspberry_pi_pico' - steps: - - name: Clean workspace - run: | - echo "Cleaning up previous run" - rm -rf "${{ github.workspace }}" - mkdir -p "${{ github.workspace }}" - - # USB bus on rpi4 is not stable, reset it before testing - - name: Reset USB bus - run: | - lsusb - lsusb -t - # reset VIA Labs 2.0 hub - sudo usbreset 001/002 - - # legacy code - #for port in $(lspci | grep USB | cut -d' ' -f1); do - # echo -n "0000:${port}"| sudo tee /sys/bus/pci/drivers/xhci_hcd/unbind; - # sleep 0.1; - # echo -n "0000:${port}" | sudo tee /sys/bus/pci/drivers/xhci_hcd/bind; - #done - - - name: Checkout test/hil - uses: actions/checkout@v4 - with: - sparse-checkout: test/hil - - - name: Download Artifacts - uses: actions/download-artifact@v4 - with: - name: ${{ matrix.board }} - path: cmake-build/cmake-build-${{ matrix.board }} - - - name: Test on actual hardware - run: | - python3 test/hil/hil_test.py --board ${{ matrix.board }} hil_pi4.json + toolchain: + - 'aarch64-gcc' + #- 'arm-clang' + - 'arm-gcc' + - 'msp430-gcc' + - 'riscv-gcc' + with: + build-system: 'make' + toolchain: ${{ matrix.toolchain }} + toolchain_url: ${{ fromJSON(needs.set-matrix.outputs.json)[matrix.toolchain].toolchain_url }} + build-family: ${{ toJSON(fromJSON(needs.set-matrix.outputs.json)[matrix.toolchain].family) }} diff --git a/.github/workflows/build_esp.yml b/.github/workflows/build_esp.yml index 4108a58a5..66fa8548e 100644 --- a/.github/workflows/build_esp.yml +++ b/.github/workflows/build_esp.yml @@ -41,14 +41,16 @@ jobs: with: python-version: '3.x' - - name: Pull ESP-IDF docker - run: docker pull espressif/idf:latest - - name: Checkout TinyUSB uses: actions/checkout@v4 + - name: Setup Toolchain + uses: ./.github/actions/setup_toolchain + with: + toolchain: 'esp-idf' + - name: Build - run: docker run --rm -v $PWD:/project -w /project espressif/idf:v5.1.1 python3 tools/build_esp32.py ${{ matrix.board }} + run: docker run --rm -v $PWD:/project -w /project espressif/idf:v5.1.1 python3 tools/build.py -b ${{ matrix.board }} - name: Upload Artifacts for Hardware Testing if: matrix.board == 'espressif_s3_devkitm' && github.repository_owner == 'hathach' @@ -91,13 +93,6 @@ jobs: # reset VIA Labs 2.0 hub sudo usbreset 001/002 - # legacy code - #for port in $(lspci | grep USB | cut -d' ' -f1); do - # echo -n "0000:${port}"| sudo tee /sys/bus/pci/drivers/xhci_hcd/unbind; - # sleep 0.1; - # echo -n "0000:${port}" | sudo tee /sys/bus/pci/drivers/xhci_hcd/bind; - #done - - name: Checkout test/hil uses: actions/checkout@v4 with: @@ -111,4 +106,4 @@ jobs: - name: Test on actual hardware run: | - python3 test/hil/hil_test.py --board ${{ matrix.board }} hil_pi4.json + python3 test/hil/hil_test.py --board ${{ matrix.board }} pi4_esp32.json diff --git a/.github/workflows/build_family.yml b/.github/workflows/build_family.yml new file mode 100644 index 000000000..2e89267a3 --- /dev/null +++ b/.github/workflows/build_family.yml @@ -0,0 +1,64 @@ +name: Build family + +on: + workflow_call: + inputs: + build-system: + required: true + type: string + toolchain: + required: true + type: string + toolchain_url: + required: true + type: string + build-family: + required: true + type: string + +jobs: + family: + runs-on: ubuntu-latest + strategy: + fail-fast: false + matrix: + family: ${{ fromJSON(inputs.build-family) }} + steps: + - name: Checkout TinyUSB + uses: actions/checkout@v4 + + - name: Setup Python + uses: actions/setup-python@v5 + with: + python-version: '3.x' + + - name: Setup Toolchain + uses: ./.github/actions/setup_toolchain + with: + toolchain: ${{ inputs.toolchain }} + toolchain_url: ${{ inputs.toolchain_url }} + + - name: Checkout pico-sdk for rp2040 + if: contains(matrix.family, 'rp2040') + uses: actions/checkout@v4 + with: + repository: raspberrypi/pico-sdk + ref: develop + path: pico-sdk + + - name: Get Dependencies + run: | + sudo apt install -y ninja-build + pip install click + python3 tools/get_deps.py ${{ matrix.family }} + + - name: Build + run: | + OPTION="" + if [[ "${{ inputs.toolchain }}" == *"clang"* ]]; then + OPTION="--toolchain clang" + fi + echo "OPTION=$OPTION" + python tools/build.py -s ${{ inputs.build-system }} $OPTION ${{ matrix.family }} + env: + PICO_SDK_PATH: ${{ github.workspace }}/pico-sdk diff --git a/.github/workflows/build_iar.yml b/.github/workflows/build_iar.yml index 6b1493a97..c4a7f96b7 100644 --- a/.github/workflows/build_iar.yml +++ b/.github/workflows/build_iar.yml @@ -52,8 +52,8 @@ jobs: run: python3 tools/get_deps.py ${{ matrix.family }} - name: Build - run: python3 tools/build_cmake.py ${{ matrix.family }} -DTOOLCHAIN=iar + run: python3 tools/build.py --toolchain iar ${{ matrix.family }} - name: Test on actual hardware (hardware in the loop) run: | - python3 test/hil/hil_test.py hil_hfp.json + python3 test/hil/hil_test.py hfp.json diff --git a/.github/workflows/build_renesas.yml b/.github/workflows/build_renesas.yml index fbc12d285..8c83bdbbf 100644 --- a/.github/workflows/build_renesas.yml +++ b/.github/workflows/build_renesas.yml @@ -64,7 +64,9 @@ jobs: run: echo >> $GITHUB_PATH `echo ~/cache/toolchain/*/bin` - name: Get Dependencies - run: python3 tools/get_deps.py ${{ matrix.family }} + run: | + pip install click + python3 tools/get_deps.py ${{ matrix.family }} - name: Build - run: python3 tools/build_make.py ${{ matrix.family }} + run: python3 tools/build.py -s make ${{ matrix.family }} diff --git a/.github/workflows/build_riscv.yml b/.github/workflows/build_riscv.yml deleted file mode 100644 index 7f5031ff1..000000000 --- a/.github/workflows/build_riscv.yml +++ /dev/null @@ -1,71 +0,0 @@ -name: Build RISC-V - -on: - workflow_dispatch: - push: - paths: - - 'src/**' - - 'examples/**' - - 'lib/**' - - 'hw/**' - - 'tools/get_deps.py' - - '.github/workflows/build_riscv.yml' - pull_request: - branches: [ master ] - paths: - - 'src/**' - - 'examples/**' - - 'lib/**' - - 'hw/**' - - 'tools/get_deps.py' - - '.github/workflows/build_riscv.yml' - -concurrency: - group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} - cancel-in-progress: true - -jobs: - build-riscv: - runs-on: ubuntu-latest - strategy: - fail-fast: false - matrix: - family: - # Alphabetical order - - 'ch32v307' - - 'fomu' - - 'gd32vf103' - steps: - - name: Setup Python - uses: actions/setup-python@v5 - with: - python-version: '3.x' - - - name: Checkout TinyUSB - uses: actions/checkout@v4 - - - name: Set Toolchain URL - run: echo >> $GITHUB_ENV TOOLCHAIN_URL=https://github.com/xpack-dev-tools/riscv-none-embed-gcc-xpack/releases/download/v10.1.0-1.1/xpack-riscv-none-embed-gcc-10.1.0-1.1-linux-x64.tar.gz - - - name: Cache Toolchain - uses: actions/cache@v4 - id: cache-toolchain - with: - path: ~/cache/ - key: ${{ runner.os }}-21-03-04-${{ env.TOOLCHAIN_URL }} - - - name: Install Toolchain - if: steps.cache-toolchain.outputs.cache-hit != 'true' - run: | - mkdir -p ~/cache/toolchain - wget --progress=dot:mega $TOOLCHAIN_URL -O toolchain.tar.gz - tar -C ~/cache/toolchain -xaf toolchain.tar.gz - - - name: Set Toolchain Path - run: echo >> $GITHUB_PATH `echo ~/cache/toolchain/*/bin` - - - name: Get Dependencies - run: python3 tools/get_deps.py ${{ matrix.family }} - - - name: Build - run: python3 tools/build_make.py ${{ matrix.family }} diff --git a/.github/workflows/build_win_mac.yml b/.github/workflows/build_win_mac.yml index b33b5b593..35328aa32 100644 --- a/.github/workflows/build_win_mac.yml +++ b/.github/workflows/build_win_mac.yml @@ -48,7 +48,9 @@ jobs: uses: actions/checkout@v4 - name: Get Dependencies - run: python3 tools/get_deps.py stm32f4 + run: | + pip install click + python3 tools/get_deps.py stm32f4 - name: Build - run: python3 tools/build_make.py stm32f4 stm32f411disco + run: python3 tools/build.py -s make stm32f2 diff --git a/.github/workflows/ci_set_matrix.py b/.github/workflows/ci_set_matrix.py new file mode 100644 index 000000000..2a17be6a1 --- /dev/null +++ b/.github/workflows/ci_set_matrix.py @@ -0,0 +1,51 @@ +import json + +# toolchain, url +toolchain_list = { + "aarch64-gcc": "https://developer.arm.com/-/media/Files/downloads/gnu-a/10.3-2021.07/binrel/gcc-arm-10.3-2021.07-x86_64-aarch64-none-elf.tar.xz", + "arm-clang": "https://github.com/ARM-software/LLVM-embedded-toolchain-for-Arm/releases/download/release-17.0.1/LLVMEmbeddedToolchainForArm-17.0.1-Linux-x86_64.tar.xz", + "arm-gcc": "", + "msp430-gcc": "http://software-dl.ti.com/msp430/msp430_public_sw/mcu/msp430/MSPGCC/9_2_0_0/export/msp430-gcc-9.2.0.50_linux64.tar.bz2", + "riscv-gcc": "https://github.com/xpack-dev-tools/riscv-none-embed-gcc-xpack/releases/download/v10.1.0-1.1/xpack-riscv-none-embed-gcc-10.1.0-1.1-linux-x64.tar.gz", +} + +# family: [supported toolchain] +family_list = { + "broadcom_32bit": ["arm-gcc"], + "broadcom_64bit": ["aarch64-gcc"], + "ch32v307 fomu gd32vf103": ["riscv-gcc"], + "imxrt": ["arm-gcc", "arm-clang"], + "kinetis_k kinetis_kl kinetis_k32l2": ["arm-gcc", "arm-clang"], + "lpc11 lpc13 lpc15": ["arm-gcc"], + "lpc17 lpc18 lpc40 lpc43": ["arm-gcc", "arm-clang"], + "lpc51 lpc54 lpc55": ["arm-gcc", "arm-clang"], + "mcx": ["arm-gcc"], + "mm32": ["arm-gcc"], + "msp430": ["msp430-gcc"], + "msp432e4 tm4c": ["arm-gcc"], + "nrf": ["arm-gcc", "arm-clang"], + "ra": ["arm-gcc"], + "rp2040": ["arm-gcc"], + "samd11 samd21 saml2x": ["arm-gcc", "arm-clang"], + "samd5x_e5x samg": ["arm-gcc", "arm-clang"], + "stm32f0 stm32f1 stm32f2 stm32f3": ["arm-gcc", "arm-clang"], + "stm32f4": ["arm-gcc", "arm-clang"], + "stm32f7": ["arm-gcc", "arm-clang"], + "stm32g0 stm32g4 stm32h5": ["arm-gcc", "arm-clang"], + "stm32h7": ["arm-gcc", "arm-clang"], + "stm32l4 stm32u5 stm32wb": ["arm-gcc", "arm-clang"], + "xmc4000": ["arm-gcc"], +} + + +def set_matrix_json(): + matrix = {} + for toolchain in toolchain_list.keys(): + filtered_families = [family for family, supported_toolchain in family_list.items() if + toolchain in supported_toolchain] + matrix[toolchain] = {"family": filtered_families, "toolchain_url": toolchain_list[toolchain]} + print(json.dumps(matrix)) + + +if __name__ == '__main__': + set_matrix_json() diff --git a/.github/workflows/cifuzz.yml b/.github/workflows/cifuzz.yml index 5dc0f2764..faa0f911c 100644 --- a/.github/workflows/cifuzz.yml +++ b/.github/workflows/cifuzz.yml @@ -12,6 +12,7 @@ on: - '**.h' jobs: Fuzzing: + if: false runs-on: ubuntu-latest steps: - name: Build Fuzzers @@ -20,12 +21,14 @@ jobs: with: oss-fuzz-project-name: 'tinyusb' language: c++ + - name: Run Fuzzers uses: google/oss-fuzz/infra/cifuzz/actions/run_fuzzers@master with: oss-fuzz-project-name: 'tinyusb' language: c++ fuzz-seconds: 600 + - name: Upload Crash uses: actions/upload-artifact@v4 if: failure() && steps.build.outcome == 'success' diff --git a/.github/workflows/codeql-buildscript.sh b/.github/workflows/codeql-buildscript.sh index 35e029922..272b55d22 100644 --- a/.github/workflows/codeql-buildscript.sh +++ b/.github/workflows/codeql-buildscript.sh @@ -1,5 +1,6 @@ #!/usr/bin/env bash FAMILY=stm32l4 +pip install click python3 tools/get_deps.py $FAMILY -python3 tools/build_make.py $FAMILY +python3 tools/build.py -s make $FAMILY diff --git a/.github/workflows/hil_test.yml b/.github/workflows/hil_test.yml new file mode 100644 index 000000000..024ab969d --- /dev/null +++ b/.github/workflows/hil_test.yml @@ -0,0 +1,125 @@ +name: Hardware Test + +on: + workflow_dispatch: + push: + paths: + - 'src/**' + - 'examples/**' + - 'lib/**' + - 'hw/**' + - 'test/hil/**' + - 'tools/get_deps.py' + - '.github/actions/**' + - '.github/workflows/hil_test.yml' + pull_request: + branches: [ master ] + paths: + - 'src/**' + - 'examples/**' + - 'lib/**' + - 'hw/**' + - 'test/hil/**' + - 'tools/get_deps.py' + - '.github/actions/**' + - '.github/workflows/hil_test.yml' +concurrency: + group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} + cancel-in-progress: true + +jobs: + build: + if: github.repository_owner == 'hathach' + runs-on: ubuntu-latest + outputs: + BOARD_LIST: ${{ steps.parse_hil_json.outputs.BOARD_LIST }} + steps: + - name: Checkout TinyUSB + uses: actions/checkout@v4 + + - name: Setup Python + uses: actions/setup-python@v5 + with: + python-version: '3.x' + + - name: Install ARM GCC + uses: carlosperate/arm-none-eabi-gcc-action@v1 + with: + release: '12.3.Rel1' + + - name: Parse HIL json + id: parse_hil_json + run: | + sudo apt install -y jq + BOARD_LIST=$(jq -r '.boards[] | "-b " + .name' test/hil/pi4.json | tr '\n' ' ') + echo "BOARD_LIST=$BOARD_LIST" + echo >> $GITHUB_ENV "BOARD_LIST=$BOARD_LIST" + echo >> $GITHUB_OUTPUT "BOARD_LIST=$BOARD_LIST" + + - name: Checkout pico-sdk for rp2040 + uses: actions/checkout@v4 + with: + repository: raspberrypi/pico-sdk + ref: develop + path: pico-sdk + + - name: Get Dependencies + run: | + pip install click + sudo apt install -y ninja-build + python3 tools/get_deps.py $BOARD_LIST + + - name: Build + run: | + python tools/build.py $BOARD_LIST + env: + PICO_SDK_PATH: ${{ github.workspace }}/pico-sdk + + - name: Upload Artifacts for Hardware Testing + uses: actions/upload-artifact@v4 + with: + name: hil_pi4 + path: | + cmake-build/cmake-build-*/*/*/*.elf + cmake-build/cmake-build-*/*/*/*.bin + + # --------------------------------------- + # Hardware in the loop (HIL) + # Current self-hosted instance is running on an RPI4. For attached hardware checkout hil_pi4.json + # --------------------------------------- + hil-pi4: + if: github.repository_owner == 'hathach' + needs: build + runs-on: [self-hosted, rp2040, nrf52840, hardware-in-the-loop] + env: + BOARD_LIST: ${{ needs.build.outputs.BOARD_LIST }} + steps: + - name: Clean workspace + run: | + echo "Cleaning up previous run" + rm -rf "${{ github.workspace }}" + mkdir -p "${{ github.workspace }}" + + # USB bus on rpi4 is not stable, reset it before testing + - name: Reset USB bus + run: | + lsusb + lsusb -t + # reset VIA Labs 2.0 hub + sudo usbreset 001/002 + + - name: Checkout TinyUSB + uses: actions/checkout@v4 + with: + sparse-checkout: test/hil + + - name: Download Artifacts + uses: actions/download-artifact@v4 + with: + name: hil_pi4 + path: cmake-build + + - name: Test on actual hardware + run: | + echo "BOARD_LIST=$BOARD_LIST" + python3 test/hil/hil_test.py $BOARD_LIST pi4.json diff --git a/.github/workflows/pre-commit.yml b/.github/workflows/pre-commit.yml index e36259daa..6b3151702 100644 --- a/.github/workflows/pre-commit.yml +++ b/.github/workflows/pre-commit.yml @@ -38,6 +38,7 @@ jobs: - name: Build Fuzzer run: | + pip install click export CC=clang export CXX=clang++ fuzz_harness=$(ls -d test/fuzz/device/*/) diff --git a/.idea/cmake.xml b/.idea/cmake.xml index 0e2ca61e4..bb13a0466 100644 --- a/.idea/cmake.xml +++ b/.idea/cmake.xml @@ -117,7 +117,7 @@ - + @@ -125,7 +125,11 @@ - + + + + + \ No newline at end of file diff --git a/examples/build_system/cmake/cpu/rv32i-ilp32.cmake b/examples/build_system/cmake/cpu/rv32i-ilp32.cmake new file mode 100644 index 000000000..b4889e6ff --- /dev/null +++ b/examples/build_system/cmake/cpu/rv32i-ilp32.cmake @@ -0,0 +1,19 @@ +if (TOOLCHAIN STREQUAL "gcc") + set(TOOLCHAIN_COMMON_FLAGS + -march=rv32i + -mabi=ilp32 + ) + set(FREERTOS_PORT GCC_RISC_V CACHE INTERNAL "") + +elseif (TOOLCHAIN STREQUAL "clang") + set(TOOLCHAIN_COMMON_FLAGS + -march=rv32i + -mabi=ilp32 + ) + set(FREERTOS_PORT GCC_RISC_V CACHE INTERNAL "") + +elseif (TOOLCHAIN STREQUAL "iar") + message(FATAL_ERROR "IAR not supported") + set(FREERTOS_PORT IAR_RISC_V CACHE INTERNAL "") + +endif () diff --git a/examples/build_system/cmake/cpu/rv32imac-ilp32.cmake b/examples/build_system/cmake/cpu/rv32imac-ilp32.cmake new file mode 100644 index 000000000..dd1bc0af7 --- /dev/null +++ b/examples/build_system/cmake/cpu/rv32imac-ilp32.cmake @@ -0,0 +1,18 @@ +if (TOOLCHAIN STREQUAL "gcc") + set(TOOLCHAIN_COMMON_FLAGS + -march=rv32imac + -mabi=ilp32 + ) + set(FREERTOS_PORT GCC_RISC_V CACHE INTERNAL "") + +elseif (TOOLCHAIN STREQUAL "clang") + set(TOOLCHAIN_COMMON_FLAGS + -march=rv32imac + -mabi=ilp32 + ) + set(FREERTOS_PORT GCC_RISC_V CACHE INTERNAL "") + +elseif (TOOLCHAIN STREQUAL "iar") + message(FATAL_ERROR "IAR not supported") + set(FREERTOS_PORT IAR_RISC_V CACHE INTERNAL "") +endif () diff --git a/examples/build_system/cmake/toolchain/riscv_gcc.cmake b/examples/build_system/cmake/toolchain/riscv_gcc.cmake new file mode 100644 index 000000000..904b27294 --- /dev/null +++ b/examples/build_system/cmake/toolchain/riscv_gcc.cmake @@ -0,0 +1,21 @@ +if (NOT DEFINED CMAKE_C_COMPILER) + set(CMAKE_C_COMPILER "riscv-none-embed-gcc") +endif () + +if (NOT DEFINED CMAKE_CXX_COMPILER) + set(CMAKE_CXX_COMPILER "riscv-none-embed-g++") +endif () + +set(CMAKE_ASM_COMPILER ${CMAKE_C_COMPILER}) +set(CMAKE_SIZE "riscv-none-embed-size" CACHE FILEPATH "") +set(CMAKE_OBJCOPY "riscv-none-embed-objcopy" CACHE FILEPATH "") +set(CMAKE_OBJDUMP "riscv-none-embed-objdump" CACHE FILEPATH "") + +include(${CMAKE_CURRENT_LIST_DIR}/common.cmake) + +get_property(IS_IN_TRY_COMPILE GLOBAL PROPERTY IN_TRY_COMPILE) +if (IS_IN_TRY_COMPILE) + set(CMAKE_C_LINK_FLAGS "${CMAKE_C_LINK_FLAGS} -nostdlib") + set(CMAKE_CXX_LINK_FLAGS "${CMAKE_CXX_LINK_FLAGS} -nostdlib") + cmake_print_variables(CMAKE_C_LINK_FLAGS) +endif () diff --git a/examples/build_system/make/cpu/rv32i-ilp32.mk b/examples/build_system/make/cpu/rv32i-ilp32.mk new file mode 100644 index 000000000..a465baf4c --- /dev/null +++ b/examples/build_system/make/cpu/rv32i-ilp32.mk @@ -0,0 +1,13 @@ +ifeq ($(TOOLCHAIN),gcc) + CFLAGS += \ + -march=rv32i \ + -mabi=ilp32 \ + +else ifeq ($(TOOLCHAIN),iar) + #CFLAGS += --cpu cortex-a53 + #ASFLAGS += --cpu cortex-a53 + +endif + +# For freeRTOS port source +FREERTOS_PORTABLE_SRC = $(FREERTOS_PORTABLE_PATH)/RISC-V diff --git a/examples/build_system/make/cpu/rv32imac-ilp32.mk b/examples/build_system/make/cpu/rv32imac-ilp32.mk new file mode 100644 index 000000000..2b6493e48 --- /dev/null +++ b/examples/build_system/make/cpu/rv32imac-ilp32.mk @@ -0,0 +1,13 @@ +ifeq ($(TOOLCHAIN),gcc) + CFLAGS += \ + -march=rv32imac \ + -mabi=ilp32 \ + +else ifeq ($(TOOLCHAIN),iar) + #CFLAGS += --cpu cortex-a53 + #ASFLAGS += --cpu cortex-a53 + +endif + +# For freeRTOS port source +FREERTOS_PORTABLE_SRC = $(FREERTOS_PORTABLE_PATH)/RISC-V diff --git a/examples/build_system/make/toolchain/riscv_gcc.mk b/examples/build_system/make/toolchain/riscv_gcc.mk new file mode 100644 index 000000000..843aff38c --- /dev/null +++ b/examples/build_system/make/toolchain/riscv_gcc.mk @@ -0,0 +1,20 @@ +# makefile for arm gcc toolchain + +# Can be set by family, default to ARM GCC +CROSS_COMPILE ?= riscv-none-embed- + +CC = $(CROSS_COMPILE)gcc +CXX = $(CROSS_COMPILE)g++ +AS = $(CC) -x assembler-with-cpp +LD = $(CC) + +GDB = $(CROSS_COMPILE)gdb +OBJCOPY = $(CROSS_COMPILE)objcopy +SIZE = $(CROSS_COMPILE)size + +CFLAGS += \ + -fsingle-precision-constant \ + +LIBS += -lgcc -lm -lnosys + +include ${TOP}/examples/build_system/make/toolchain/gcc_common.mk diff --git a/examples/device/video_capture/skip.txt b/examples/device/video_capture/skip.txt index db64cc639..5898664a2 100644 --- a/examples/device/video_capture/skip.txt +++ b/examples/device/video_capture/skip.txt @@ -1,4 +1,3 @@ mcu:MSP430x5xx mcu:NUC121 mcu:SAMD11 -family:espressif diff --git a/hw/bsp/ch32v307/boards/ch32v307v_r1_1v0/board.cmake b/hw/bsp/ch32v307/boards/ch32v307v_r1_1v0/board.cmake new file mode 100644 index 000000000..9f5682042 --- /dev/null +++ b/hw/bsp/ch32v307/boards/ch32v307v_r1_1v0/board.cmake @@ -0,0 +1,4 @@ +function(update_board TARGET) +# target_compile_definitions(${TARGET} PUBLIC +# ) +endfunction() diff --git a/hw/bsp/ch32v307/boards/ch32v307v_r1_1v0/debug_uart.c b/hw/bsp/ch32v307/boards/ch32v307v_r1_1v0/debug_uart.c deleted file mode 100644 index db3551ca7..000000000 --- a/hw/bsp/ch32v307/boards/ch32v307v_r1_1v0/debug_uart.c +++ /dev/null @@ -1,110 +0,0 @@ -/* - * The MIT License (MIT) - * - * Copyright (c) 2022 Greg Davill - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - * - * This file is part of the TinyUSB stack. - */ - -#include "debug_uart.h" -#include - - -#define UART_RINGBUFFER_SIZE_TX 64 -#define UART_RINGBUFFER_MASK_TX (UART_RINGBUFFER_SIZE_TX-1) - -static char tx_buf[UART_RINGBUFFER_SIZE_TX]; -static unsigned int tx_produce; -static volatile unsigned int tx_consume; - -void USART1_IRQHandler(void) __attribute__((naked)); -void USART1_IRQHandler(void) { - __asm volatile ("call USART1_IRQHandler_impl; mret"); -} - -__attribute__((used)) void USART1_IRQHandler_impl(void) -{ - if(USART_GetITStatus(USART1, USART_IT_TC) != RESET) - { - USART_ClearITPendingBit(USART1, USART_IT_TC); - - if(tx_consume != tx_produce) { - USART_SendData(USART1, tx_buf[tx_consume]); - tx_consume = (tx_consume + 1) & UART_RINGBUFFER_MASK_TX; - } - } - -} - -void uart_write(char c) -{ - unsigned int tx_produce_next = (tx_produce + 1) & UART_RINGBUFFER_MASK_TX; - - NVIC_DisableIRQ(USART1_IRQn); - if((tx_consume != tx_produce) || (USART_GetFlagStatus(USART1, USART_FLAG_TXE) == RESET)) { - tx_buf[tx_produce] = c; - tx_produce = tx_produce_next; - } else { - USART_SendData(USART1, c); - } - NVIC_EnableIRQ(USART1_IRQn); -} - - -void uart_sync(void) -{ - while(tx_consume != tx_produce); -} - - -void usart_printf_init(uint32_t baudrate) -{ - GPIO_InitTypeDef GPIO_InitStructure; - USART_InitTypeDef USART_InitStructure; - - tx_produce = 0; - tx_consume = 0; - - RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1 | RCC_APB2Periph_GPIOA, ENABLE); - - GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9; - GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; - GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; - GPIO_Init(GPIOA, &GPIO_InitStructure); - - USART_InitStructure.USART_BaudRate = baudrate; - USART_InitStructure.USART_WordLength = USART_WordLength_8b; - USART_InitStructure.USART_StopBits = USART_StopBits_1; - USART_InitStructure.USART_Parity = USART_Parity_No; - USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; - USART_InitStructure.USART_Mode = USART_Mode_Tx; - - USART_Init(USART1, &USART_InitStructure); - USART_ITConfig(USART1, USART_IT_TC, ENABLE); - USART_Cmd(USART1, ENABLE); - - NVIC_InitTypeDef NVIC_InitStructure = { 0 }; - NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn; - NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1; - NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3; - NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; - NVIC_Init(&NVIC_InitStructure); -} diff --git a/hw/bsp/ch32v307/boards/ch32v307v_r1_1v0/debug_uart.h b/hw/bsp/ch32v307/boards/ch32v307v_r1_1v0/debug_uart.h deleted file mode 100644 index a7e070585..000000000 --- a/hw/bsp/ch32v307/boards/ch32v307v_r1_1v0/debug_uart.h +++ /dev/null @@ -1,31 +0,0 @@ -/* - * The MIT License (MIT) - * - * Copyright (c) 2022 Greg Davill - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - * - * This file is part of the TinyUSB stack. - */ - -#include - -void uart_write(char c); -void uart_sync(void); -void usart_printf_init(uint32_t baudrate); diff --git a/hw/bsp/ch32v307/debug_uart.c b/hw/bsp/ch32v307/debug_uart.c new file mode 100644 index 000000000..db3551ca7 --- /dev/null +++ b/hw/bsp/ch32v307/debug_uart.c @@ -0,0 +1,110 @@ +/* + * The MIT License (MIT) + * + * Copyright (c) 2022 Greg Davill + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + * + * This file is part of the TinyUSB stack. + */ + +#include "debug_uart.h" +#include + + +#define UART_RINGBUFFER_SIZE_TX 64 +#define UART_RINGBUFFER_MASK_TX (UART_RINGBUFFER_SIZE_TX-1) + +static char tx_buf[UART_RINGBUFFER_SIZE_TX]; +static unsigned int tx_produce; +static volatile unsigned int tx_consume; + +void USART1_IRQHandler(void) __attribute__((naked)); +void USART1_IRQHandler(void) { + __asm volatile ("call USART1_IRQHandler_impl; mret"); +} + +__attribute__((used)) void USART1_IRQHandler_impl(void) +{ + if(USART_GetITStatus(USART1, USART_IT_TC) != RESET) + { + USART_ClearITPendingBit(USART1, USART_IT_TC); + + if(tx_consume != tx_produce) { + USART_SendData(USART1, tx_buf[tx_consume]); + tx_consume = (tx_consume + 1) & UART_RINGBUFFER_MASK_TX; + } + } + +} + +void uart_write(char c) +{ + unsigned int tx_produce_next = (tx_produce + 1) & UART_RINGBUFFER_MASK_TX; + + NVIC_DisableIRQ(USART1_IRQn); + if((tx_consume != tx_produce) || (USART_GetFlagStatus(USART1, USART_FLAG_TXE) == RESET)) { + tx_buf[tx_produce] = c; + tx_produce = tx_produce_next; + } else { + USART_SendData(USART1, c); + } + NVIC_EnableIRQ(USART1_IRQn); +} + + +void uart_sync(void) +{ + while(tx_consume != tx_produce); +} + + +void usart_printf_init(uint32_t baudrate) +{ + GPIO_InitTypeDef GPIO_InitStructure; + USART_InitTypeDef USART_InitStructure; + + tx_produce = 0; + tx_consume = 0; + + RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1 | RCC_APB2Periph_GPIOA, ENABLE); + + GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9; + GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; + GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; + GPIO_Init(GPIOA, &GPIO_InitStructure); + + USART_InitStructure.USART_BaudRate = baudrate; + USART_InitStructure.USART_WordLength = USART_WordLength_8b; + USART_InitStructure.USART_StopBits = USART_StopBits_1; + USART_InitStructure.USART_Parity = USART_Parity_No; + USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; + USART_InitStructure.USART_Mode = USART_Mode_Tx; + + USART_Init(USART1, &USART_InitStructure); + USART_ITConfig(USART1, USART_IT_TC, ENABLE); + USART_Cmd(USART1, ENABLE); + + NVIC_InitTypeDef NVIC_InitStructure = { 0 }; + NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn; + NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1; + NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3; + NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; + NVIC_Init(&NVIC_InitStructure); +} diff --git a/hw/bsp/ch32v307/debug_uart.h b/hw/bsp/ch32v307/debug_uart.h new file mode 100644 index 000000000..a7e070585 --- /dev/null +++ b/hw/bsp/ch32v307/debug_uart.h @@ -0,0 +1,31 @@ +/* + * The MIT License (MIT) + * + * Copyright (c) 2022 Greg Davill + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + * + * This file is part of the TinyUSB stack. + */ + +#include + +void uart_write(char c); +void uart_sync(void); +void usart_printf_init(uint32_t baudrate); diff --git a/hw/bsp/ch32v307/family.cmake b/hw/bsp/ch32v307/family.cmake new file mode 100644 index 000000000..87a0f2eba --- /dev/null +++ b/hw/bsp/ch32v307/family.cmake @@ -0,0 +1,114 @@ +include_guard() + +set(SDK_DIR ${TOP}/hw/mcu/wch/ch32v307/EVT/EXAM/SRC) + +# include board specific +include(${CMAKE_CURRENT_LIST_DIR}/boards/${BOARD}/board.cmake) + +# toolchain set up +set(CMAKE_SYSTEM_PROCESSOR rv32imac-ilp32 CACHE INTERNAL "System Processor") +set(CMAKE_TOOLCHAIN_FILE ${TOP}/examples/build_system/cmake/toolchain/riscv_${TOOLCHAIN}.cmake) + +set(FAMILY_MCUS CH32V307 CACHE INTERNAL "") +set(OPENOCD_OPTION "-f ${CMAKE_CURRENT_LIST_DIR}/wch-riscv.cfg") +set(OPENOCD_OPTION2 "-c wlink_reset_resume") + +#------------------------------------ +# BOARD_TARGET +#------------------------------------ +# only need to be built ONCE for all examples +function(add_board_target BOARD_TARGET) + if (TARGET ${BOARD_TARGET}) + return() + endif() + + if (NOT DEFINED LD_FILE_GNU) + set(LD_FILE_GNU ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/ch32v307.ld) + endif () + set(LD_FILE_Clang ${LD_FILE_GNU}) + + if (NOT DEFINED STARTUP_FILE_GNU) + set(STARTUP_FILE_GNU ${SDK_DIR}/Startup/startup_ch32v30x_D8C.S) + endif () + set(STARTUP_FILE_Clang ${STARTUP_FILE_GNU}) + + add_library(${BOARD_TARGET} STATIC + ${SDK_DIR}/Core/core_riscv.c + ${SDK_DIR}/Peripheral/src/ch32v30x_gpio.c + ${SDK_DIR}/Peripheral/src/ch32v30x_misc.c + ${SDK_DIR}/Peripheral/src/ch32v30x_rcc.c + ${SDK_DIR}/Peripheral/src/ch32v30x_usart.c + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/ch32v30x_it.c + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/system_ch32v30x.c + ${STARTUP_FILE_${CMAKE_C_COMPILER_ID}} + ) + target_include_directories(${BOARD_TARGET} PUBLIC + ${SDK_DIR}/Peripheral/inc + ${CMAKE_CURRENT_FUNCTION_LIST_DIR} + ) + target_compile_definitions(${BOARD_TARGET} PUBLIC + BOARD_TUD_MAX_SPEED=OPT_MODE_HIGH_SPEED + ) + + update_board(${BOARD_TARGET}) + + if (CMAKE_C_COMPILER_ID STREQUAL "GNU") + target_compile_options(${BOARD_TARGET} PUBLIC + -msmall-data-limit=8 + -mno-save-restore + -fmessage-length=0 + -fsigned-char + ) + target_link_options(${BOARD_TARGET} PUBLIC + "LINKER:--script=${LD_FILE_GNU}" + -nostartfiles + --specs=nosys.specs --specs=nano.specs + ) + elseif (CMAKE_C_COMPILER_ID STREQUAL "Clang") + message(FATAL_ERROR "Clang is not supported for MSP432E4") + elseif (CMAKE_C_COMPILER_ID STREQUAL "IAR") + target_link_options(${BOARD_TARGET} PUBLIC + "LINKER:--config=${LD_FILE_IAR}" + ) + endif () +endfunction() + + +#------------------------------------ +# Functions +#------------------------------------ +function(family_configure_example TARGET RTOS) + family_configure_common(${TARGET} ${RTOS}) + + # Board target + add_board_target(board_${BOARD}) + + #---------- Port Specific ---------- + # These files are built for each example since it depends on example's tusb_config.h + target_sources(${TARGET} PUBLIC + # BSP + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/family.c + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/debug_uart.c + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/../board.c + ) + target_include_directories(${TARGET} PUBLIC + # family, hw, board + ${CMAKE_CURRENT_FUNCTION_LIST_DIR} + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/../../ + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/boards/${BOARD} + ) + + # Add TinyUSB target and port source + family_add_tinyusb(${TARGET} OPT_MCU_CH32V307 ${RTOS}) + target_sources(${TARGET}-tinyusb PUBLIC + ${TOP}/src/portable/wch/dcd_ch32_usbhs.c + ) + target_link_libraries(${TARGET}-tinyusb PUBLIC board_${BOARD}) + + # Link dependencies + target_link_libraries(${TARGET} PUBLIC board_${BOARD} ${TARGET}-tinyusb) + + # Flashing + family_add_bin_hex(${TARGET}) + family_flash_openocd_wch(${TARGET}) +endfunction() diff --git a/hw/bsp/ch32v307/family.mk b/hw/bsp/ch32v307/family.mk index 07e57f04c..003b90539 100644 --- a/hw/bsp/ch32v307/family.mk +++ b/hw/bsp/ch32v307/family.mk @@ -6,29 +6,28 @@ CROSS_COMPILE ?= riscv-none-embed- # Submodules CH32V307_SDK = hw/mcu/wch/ch32v307 -DEPS_SUBMODULES += $(CH32V307_SDK) # WCH-SDK paths CH32V307_SDK_SRC = $(CH32V307_SDK)/EVT/EXAM/SRC include $(TOP)/$(BOARD_PATH)/board.mk +CPU_CORE ?= rv32imac-ilp32 CFLAGS += \ -flto \ - -march=rv32imac \ - -mabi=ilp32 \ -msmall-data-limit=8 \ -mno-save-restore -Os \ -fmessage-length=0 \ -fsigned-char \ -ffunction-sections \ -fdata-sections \ - -nostdlib -nostartfiles \ -DCFG_TUSB_MCU=OPT_MCU_CH32V307 \ -Xlinker --gc-sections \ -DBOARD_TUD_MAX_SPEED=OPT_MODE_HIGH_SPEED -LDFLAGS_GCC += -specs=nosys.specs -specs=nano.specs +LDFLAGS_GCC += \ + -nostdlib -nostartfiles \ + --specs=nosys.specs --specs=nano.specs SRC_C += \ src/portable/wch/dcd_ch32_usbhs.c \ @@ -62,5 +61,6 @@ FREERTOS_PORTABLE_SRC = $(FREERTOS_PORTABLE_PATH)/RISC-V # openocd binaries will be generated in riscv-openocd-wch/src # flash target ROM bootloader +OPENOCD_WCH = /home/${USER}/app/riscv-openocd-wch/src/openocd flash: $(BUILD)/$(PROJECT).elf - openocd -f $(TOP)/$(FAMILY_PATH)/wch-riscv.cfg -c init -c halt -c "program $<" -c wlink_reset_resume -c exit + $(OPENOCD_WCH) -f $(TOP)/$(FAMILY_PATH)/wch-riscv.cfg -c init -c halt -c "program $<" -c wlink_reset_resume -c exit diff --git a/hw/bsp/espressif/components/led_strip/examples/led_strip_rmt_ws2812/dependencies.lock b/hw/bsp/espressif/components/led_strip/examples/led_strip_rmt_ws2812/dependencies.lock deleted file mode 100644 index 97840a153..000000000 --- a/hw/bsp/espressif/components/led_strip/examples/led_strip_rmt_ws2812/dependencies.lock +++ /dev/null @@ -1,15 +0,0 @@ -dependencies: - espressif/led_strip: - component_hash: null - source: - path: /home/hathach/code/idf-extra-components/led_strip - type: local - version: 2.5.2 - idf: - component_hash: null - source: - type: idf - version: 5.1.1 -manifest_hash: 47d47762be26168b388cb0e6cbfee6b22c68d630ebf4b27a49c47c4c54191590 -target: esp32s3 -version: 1.0.0 diff --git a/hw/bsp/family_support.cmake b/hw/bsp/family_support.cmake index bac1ecb5f..df4f616ef 100644 --- a/hw/bsp/family_support.cmake +++ b/hw/bsp/family_support.cmake @@ -385,6 +385,10 @@ function(family_flash_jlink TARGET) set(JLINKEXE JLinkExe) endif () + if (NOT DEFINED JLINK_IF) + set(JLINK_IF swd) + endif () + file(GENERATE OUTPUT $/${TARGET}.jlink CONTENT "halt @@ -396,7 +400,7 @@ exit" add_custom_target(${TARGET}-jlink DEPENDS ${TARGET} - COMMAND ${JLINKEXE} -device ${JLINK_DEVICE} -if swd -JTAGConf -1,-1 -speed auto -CommandFile $/${TARGET}.jlink + COMMAND ${JLINKEXE} -device ${JLINK_DEVICE} -if ${JLINK_IF} -JTAGConf -1,-1 -speed auto -CommandFile $/${TARGET}.jlink ) endfunction() @@ -420,16 +424,30 @@ function(family_flash_openocd TARGET) set(OPENOCD openocd) endif () - separate_arguments(OPENOCD_OPTION_LIST UNIX_COMMAND ${OPENOCD_OPTION}) + if (NOT DEFINED OPENOCD_OPTION2) + set(OPENOCD_OPTION2 "") + endif () + + separate_arguments(OPTION_LIST UNIX_COMMAND ${OPENOCD_OPTION}) + separate_arguments(OPTION_LIST2 UNIX_COMMAND ${OPENOCD_OPTION2}) # note skip verify since it has issue with rp2040 add_custom_target(${TARGET}-openocd DEPENDS ${TARGET} - COMMAND ${OPENOCD} ${OPENOCD_OPTION_LIST} -c "program $ reset exit" + COMMAND ${OPENOCD} ${OPTION_LIST} -c "program $ reset" ${OPTION_LIST2} -c exit VERBATIM ) endfunction() +# Add flash openocd-wch target +function(family_flash_openocd_wch TARGET) + if (NOT DEFINED OPENOCD) + set(OPENOCD $ENV{HOME}/app/riscv-openocd-wch/src/openocd) + endif () + + family_flash_openocd(${TARGET}) +endfunction() + # Add flash pycod target function(family_flash_pyocd TARGET) if (NOT DEFINED PYOC) diff --git a/hw/bsp/fomu/boards/fomu/board.cmake b/hw/bsp/fomu/boards/fomu/board.cmake new file mode 100644 index 000000000..9f5682042 --- /dev/null +++ b/hw/bsp/fomu/boards/fomu/board.cmake @@ -0,0 +1,4 @@ +function(update_board TARGET) +# target_compile_definitions(${TARGET} PUBLIC +# ) +endfunction() diff --git a/hw/bsp/fomu/family.c b/hw/bsp/fomu/family.c new file mode 100644 index 000000000..ccf2b12f4 --- /dev/null +++ b/hw/bsp/fomu/family.c @@ -0,0 +1,121 @@ +/* + * The MIT License (MIT) + * + * Copyright (c) 2019 Ha Thach (tinyusb.org) + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + * + * This file is part of the TinyUSB stack. + */ + +#include +#include +#include "csr.h" +#include "irq.h" + +#include "bsp/board_api.h" + +//--------------------------------------------------------------------+ +// Board porting API +//--------------------------------------------------------------------+ + +void fomu_error(uint32_t line) +{ + (void)line; + TU_BREAKPOINT(); +} + +volatile uint32_t system_ticks = 0; +static void timer_init(void) +{ + int t; + + timer0_en_write(0); + t = CONFIG_CLOCK_FREQUENCY / 1000; // 1000 kHz tick + timer0_reload_write(t); + timer0_load_write(t); + timer0_en_write(1); + timer0_ev_enable_write(1); + timer0_ev_pending_write(1); + irq_setmask(irq_getmask() | (1 << TIMER0_INTERRUPT)); +} + +void isr(void) +{ + unsigned int irqs; + + irqs = irq_pending() & irq_getmask(); + +#if CFG_TUD_ENABLED + if (irqs & (1 << USB_INTERRUPT)) { + tud_int_handler(0); + } +#endif + if (irqs & (1 << TIMER0_INTERRUPT)) { + system_ticks++; + timer0_ev_pending_write(1); + } +} + +void board_init(void) +{ + irq_setmask(0); + irq_setie(1); + timer_init(); + return; +} + +void board_led_write(bool state) +{ + rgb_ctrl_write(0xff); + rgb_raw_write(state); +} + +uint32_t board_button_read(void) +{ + return 0; +} + +int board_uart_read(uint8_t* buf, int len) +{ + (void) buf; + (void) len; + return 0; +} + +int board_uart_write(void const * buf, int len) +{ + int32_t offset = 0; + uint8_t const* buf8 = (uint8_t const*) buf; + for (offset = 0; offset < len; offset++) + { + if (!(messible_status_read() & CSR_MESSIBLE_STATUS_FULL_OFFSET)) + { + messible_in_write(buf8[offset]); + } + } + return len; +} + +#if CFG_TUSB_OS == OPT_OS_NONE +uint32_t board_millis(void) +{ + return system_ticks; +} +#endif diff --git a/hw/bsp/fomu/family.cmake b/hw/bsp/fomu/family.cmake new file mode 100644 index 000000000..8d5ab144c --- /dev/null +++ b/hw/bsp/fomu/family.cmake @@ -0,0 +1,91 @@ +include_guard() + +# include board specific +include(${CMAKE_CURRENT_LIST_DIR}/boards/${BOARD}/board.cmake) + +# toolchain set up +set(CMAKE_SYSTEM_PROCESSOR rv32i-ilp32 CACHE INTERNAL "System Processor") +set(CMAKE_TOOLCHAIN_FILE ${TOP}/examples/build_system/cmake/toolchain/riscv_${TOOLCHAIN}.cmake) + +set(FAMILY_MCUS VALENTYUSB_EPTRI CACHE INTERNAL "") + +#------------------------------------ +# BOARD_TARGET +#------------------------------------ +# only need to be built ONCE for all examples +function(add_board_target BOARD_TARGET) + if (TARGET ${BOARD_TARGET}) + return() + endif() + + if (NOT DEFINED LD_FILE_GNU) + set(LD_FILE_GNU ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/fomu.ld) + endif () + set(LD_FILE_Clang ${LD_FILE_GNU}) + + if (NOT DEFINED STARTUP_FILE_GNU) + set(STARTUP_FILE_GNU ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/crt0-vexriscv.S) + endif () + set(STARTUP_FILE_Clang ${STARTUP_FILE_GNU}) + + add_library(${BOARD_TARGET} STATIC + ${STARTUP_FILE_${CMAKE_C_COMPILER_ID}} + ) + target_include_directories(${BOARD_TARGET} PUBLIC + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/include + ) + + update_board(${BOARD_TARGET}) + + if (CMAKE_C_COMPILER_ID STREQUAL "GNU") + target_link_options(${BOARD_TARGET} PUBLIC + "LINKER:--script=${LD_FILE_GNU}" + -nostartfiles + --specs=nosys.specs --specs=nano.specs + ) + elseif (CMAKE_C_COMPILER_ID STREQUAL "Clang") + message(FATAL_ERROR "Clang is not supported for MSP432E4") + elseif (CMAKE_C_COMPILER_ID STREQUAL "IAR") + target_link_options(${BOARD_TARGET} PUBLIC + "LINKER:--config=${LD_FILE_IAR}" + ) + endif () +endfunction() + + +#------------------------------------ +# Functions +#------------------------------------ +function(family_configure_example TARGET RTOS) + family_configure_common(${TARGET} ${RTOS}) + + # Board target + add_board_target(board_${BOARD}) + + #---------- Port Specific ---------- + # These files are built for each example since it depends on example's tusb_config.h + target_sources(${TARGET} PUBLIC + # BSP + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/family.c + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/../board.c + ) + target_include_directories(${TARGET} PUBLIC + # family, hw, board + ${CMAKE_CURRENT_FUNCTION_LIST_DIR} + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/../../ + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/boards/${BOARD} + ) + + # Add TinyUSB target and port source + family_add_tinyusb(${TARGET} OPT_MCU_VALENTYUSB_EPTRI ${RTOS}) + target_sources(${TARGET}-tinyusb PUBLIC + ${TOP}/src/portable/valentyusb/eptri/dcd_eptri.c + ) + target_link_libraries(${TARGET}-tinyusb PUBLIC board_${BOARD}) + + # Link dependencies + target_link_libraries(${TARGET} PUBLIC board_${BOARD} ${TARGET}-tinyusb) + + # Flashing + family_add_bin_hex(${TARGET}) +endfunction() diff --git a/hw/bsp/fomu/family.mk b/hw/bsp/fomu/family.mk index f8a3c9ebf..d4b6eaea6 100644 --- a/hw/bsp/fomu/family.mk +++ b/hw/bsp/fomu/family.mk @@ -1,14 +1,15 @@ # Toolchain from https://github.com/xpack-dev-tools/riscv-none-embed-gcc-xpack CROSS_COMPILE = riscv-none-embed- +CPU_CORE ?= rv32i-ilp32 + CFLAGS += \ -flto \ - -march=rv32i \ - -mabi=ilp32 \ - -nostdlib \ -DCFG_TUSB_MCU=OPT_MCU_VALENTYUSB_EPTRI -LDFLAGS_GCC += -specs=nosys.specs -specs=nano.specs +LDFLAGS_GCC += \ + -nostdlib \ + --specs=nosys.specs --specs=nano.specs \ # All source paths should be relative to the top level. LD_FILE = $(FAMILY_PATH)/fomu.ld diff --git a/hw/bsp/fomu/fomu.c b/hw/bsp/fomu/fomu.c deleted file mode 100644 index d155b743d..000000000 --- a/hw/bsp/fomu/fomu.c +++ /dev/null @@ -1,120 +0,0 @@ -/* - * The MIT License (MIT) - * - * Copyright (c) 2019 Ha Thach (tinyusb.org) - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - * - * This file is part of the TinyUSB stack. - */ - -#include -#include -#include "../board_api.h" -#include "csr.h" -#include "irq.h" - -//--------------------------------------------------------------------+ -// Board porting API -//--------------------------------------------------------------------+ - -void fomu_error(uint32_t line) -{ - (void)line; - TU_BREAKPOINT(); -} - -volatile uint32_t system_ticks = 0; -static void timer_init(void) -{ - int t; - - timer0_en_write(0); - t = CONFIG_CLOCK_FREQUENCY / 1000; // 1000 kHz tick - timer0_reload_write(t); - timer0_load_write(t); - timer0_en_write(1); - timer0_ev_enable_write(1); - timer0_ev_pending_write(1); - irq_setmask(irq_getmask() | (1 << TIMER0_INTERRUPT)); -} - -void isr(void) -{ - unsigned int irqs; - - irqs = irq_pending() & irq_getmask(); - -#if CFG_TUD_ENABLED - if (irqs & (1 << USB_INTERRUPT)) { - tud_int_handler(0); - } -#endif - if (irqs & (1 << TIMER0_INTERRUPT)) { - system_ticks++; - timer0_ev_pending_write(1); - } -} - -void board_init(void) -{ - irq_setmask(0); - irq_setie(1); - timer_init(); - return; -} - -void board_led_write(bool state) -{ - rgb_ctrl_write(0xff); - rgb_raw_write(state); -} - -uint32_t board_button_read(void) -{ - return 0; -} - -int board_uart_read(uint8_t* buf, int len) -{ - (void) buf; - (void) len; - return 0; -} - -int board_uart_write(void const * buf, int len) -{ - int32_t offset = 0; - uint8_t const* buf8 = (uint8_t const*) buf; - for (offset = 0; offset < len; offset++) - { - if (!(messible_status_read() & CSR_MESSIBLE_STATUS_FULL_OFFSET)) - { - messible_in_write(buf8[offset]); - } - } - return len; -} - -#if CFG_TUSB_OS == OPT_OS_NONE -uint32_t board_millis(void) -{ - return system_ticks; -} -#endif diff --git a/hw/bsp/gd32vf103/boards/sipeed_longan_nano/board.cmake b/hw/bsp/gd32vf103/boards/sipeed_longan_nano/board.cmake new file mode 100644 index 000000000..403ac08cf --- /dev/null +++ b/hw/bsp/gd32vf103/boards/sipeed_longan_nano/board.cmake @@ -0,0 +1,13 @@ +set(JLINK_DEVICE gd32vf103cbt6) + +set(SDK_BSP_DIR ${SOC_DIR}/Board/gd32vf103c_longan_nano) +set(LD_FILE_GNU ${SDK_BSP_DIR}/Source/GCC/gcc_gd32vf103xb_flashxip.ld) + +function(update_board TARGET) + target_sources(${TARGET} PUBLIC + ${SDK_BSP_DIR}/Source/gd32vf103c_longan_nano.c + ) + target_include_directories(${TARGET} PUBLIC + ${SDK_BSP_DIR}/Include + ) +endfunction() diff --git a/hw/bsp/gd32vf103/boards/sipeed_longan_nano/board.mk b/hw/bsp/gd32vf103/boards/sipeed_longan_nano/board.mk index 3b8944452..fc49b7317 100644 --- a/hw/bsp/gd32vf103/boards/sipeed_longan_nano/board.mk +++ b/hw/bsp/gd32vf103/boards/sipeed_longan_nano/board.mk @@ -10,4 +10,3 @@ INC += $(TOP)/$(LONGAN_NANO_SDK_BSP)/Include # Longan Nano 128k ROM 32k RAM JLINK_DEVICE = gd32vf103cbt6 -#JLINK_DEVICE = gd32vf103c8t6 # Longan Nano Lite 64k ROM 20k RAM diff --git a/hw/bsp/gd32vf103/family.c b/hw/bsp/gd32vf103/family.c index 27d7e87bb..d4a819fb3 100644 --- a/hw/bsp/gd32vf103/family.c +++ b/hw/bsp/gd32vf103/family.c @@ -24,11 +24,11 @@ * This file is part of the TinyUSB stack. */ -#include "board.h" #include "drv_usb_hw.h" #include "drv_usb_dev.h" -#include "../board_api.h" +#include "bsp/board_api.h" +#include "board.h" //--------------------------------------------------------------------+ // Forward USB interrupt events to TinyUSB IRQ Handler diff --git a/hw/bsp/gd32vf103/family.cmake b/hw/bsp/gd32vf103/family.cmake new file mode 100644 index 000000000..5f4a3da8d --- /dev/null +++ b/hw/bsp/gd32vf103/family.cmake @@ -0,0 +1,119 @@ +include_guard() + +set(SDK_DIR ${TOP}/hw/mcu/gd/nuclei-sdk) +set(SOC_DIR ${SDK_DIR}/SoC/gd32vf103) + +# include board specific +include(${CMAKE_CURRENT_LIST_DIR}/boards/${BOARD}/board.cmake) + +# toolchain set up +set(CMAKE_SYSTEM_PROCESSOR rv32imac-ilp32 CACHE INTERNAL "System Processor") +set(CMAKE_TOOLCHAIN_FILE ${TOP}/examples/build_system/cmake/toolchain/riscv_${TOOLCHAIN}.cmake) + +set(FAMILY_MCUS GD32VF103 CACHE INTERNAL "") + +set(JLINK_IF jtag) + +#------------------------------------ +# BOARD_TARGET +#------------------------------------ +# only need to be built ONCE for all examples +function(add_board_target BOARD_TARGET) + if (TARGET ${BOARD_TARGET}) + return() + endif() + + if (NOT DEFINED LD_FILE_GNU) + message(FATAL_ERROR "LD_FILE_GNU is not defined") + endif () + set(LD_FILE_Clang ${LD_FILE_GNU}) + + if (NOT DEFINED STARTUP_FILE_GNU) + set(STARTUP_FILE_GNU + ${SOC_DIR}/Common/Source/GCC/startup_gd32vf103.S + ${SOC_DIR}/Common/Source/GCC/intexc_gd32vf103.S + ) + endif () + set(STARTUP_FILE_Clang ${STARTUP_FILE_GNU}) + + add_library(${BOARD_TARGET} STATIC + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/system_gd32vf103.c + ${SOC_DIR}/Common/Source/Drivers/gd32vf103_rcu.c + ${SOC_DIR}/Common/Source/Drivers/gd32vf103_gpio.c + ${SOC_DIR}/Common/Source/Drivers/Usb/gd32vf103_usb_hw.c + ${SOC_DIR}/Common/Source/Drivers/gd32vf103_usart.c + ${STARTUP_FILE_${CMAKE_C_COMPILER_ID}} + ) + target_include_directories(${BOARD_TARGET} PUBLIC + ${SDK_DIR}/NMSIS/Core/Include + ${SOC_DIR}/Common/Include + ${SOC_DIR}/Common/Include/Usb + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/boards/${BOARD} + ) + target_compile_definitions(${BOARD_TARGET} PUBLIC + DOWNLOAD_MODE=DOWNLOAD_MODE_FLASHXIP + ) + + update_board(${BOARD_TARGET}) + + if (CMAKE_C_COMPILER_ID STREQUAL "GNU") + target_compile_options(${BOARD_TARGET} PUBLIC + -mcmodel=medlow + -mstrict-align + ) + target_link_options(${BOARD_TARGET} PUBLIC + "LINKER:--script=${LD_FILE_GNU}" + -nostartfiles + ) + elseif (CMAKE_C_COMPILER_ID STREQUAL "Clang") + message(FATAL_ERROR "Clang is not supported for MSP432E4") + elseif (CMAKE_C_COMPILER_ID STREQUAL "IAR") + target_link_options(${BOARD_TARGET} PUBLIC + "LINKER:--config=${LD_FILE_IAR}" + ) + endif () +endfunction() + + +#------------------------------------ +# Functions +#------------------------------------ +function(family_configure_example TARGET RTOS) + family_configure_common(${TARGET} ${RTOS}) + + # Board target + add_board_target(board_${BOARD}) + + #---------- Port Specific ---------- + # These files are built for each example since it depends on example's tusb_config.h + target_sources(${TARGET} PUBLIC + # BSP + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/family.c + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/../board.c + ${SOC_DIR}/Common/Source/Stubs/sbrk.c + ${SOC_DIR}/Common/Source/Stubs/close.c + ${SOC_DIR}/Common/Source/Stubs/isatty.c + ${SOC_DIR}/Common/Source/Stubs/fstat.c + ${SOC_DIR}/Common/Source/Stubs/lseek.c + ${SOC_DIR}/Common/Source/Stubs/read.c + ) + target_include_directories(${TARGET} PUBLIC + # family, hw, board + ${CMAKE_CURRENT_FUNCTION_LIST_DIR} + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/../../ + ${CMAKE_CURRENT_FUNCTION_LIST_DIR}/boards/${BOARD} + ) + + # Add TinyUSB target and port source + family_add_tinyusb(${TARGET} OPT_MCU_GD32VF103 ${RTOS}) + target_sources(${TARGET}-tinyusb PUBLIC + ${TOP}/src/portable/synopsys/dwc2/dcd_dwc2.c + ) + target_link_libraries(${TARGET}-tinyusb PUBLIC board_${BOARD}) + + # Link dependencies + target_link_libraries(${TARGET} PUBLIC board_${BOARD} ${TARGET}-tinyusb) + + # Flashing + family_flash_jlink(${TARGET}) +endfunction() diff --git a/hw/bsp/gd32vf103/family.mk b/hw/bsp/gd32vf103/family.mk index 1725559c4..28e48a6b5 100644 --- a/hw/bsp/gd32vf103/family.mk +++ b/hw/bsp/gd32vf103/family.mk @@ -9,7 +9,6 @@ CROSS_COMPILE ?= riscv-none-embed- # Submodules NUCLEI_SDK = hw/mcu/gd/nuclei-sdk -DEPS_SUBMODULES += $(NUCLEI_SDK) # Nuclei-SDK paths GD32VF103_SDK_SOC = $(NUCLEI_SDK)/SoC/gd32vf103 @@ -18,12 +17,9 @@ LIBC_STUBS = $(GD32VF103_SDK_SOC)/Common/Source/Stubs STARTUP_ASM = $(GD32VF103_SDK_SOC)/Common/Source/GCC include $(TOP)/$(BOARD_PATH)/board.mk - -SKIP_NANOLIB = 1 +CPU_CORE ?= rv32imac-ilp32 CFLAGS += \ - -march=rv32imac \ - -mabi=ilp32 \ -mcmodel=medlow \ -mstrict-align \ -nostdlib -nostartfiles \ @@ -35,10 +31,10 @@ CFLAGS += -Wno-error=unused-parameter SRC_C += \ src/portable/synopsys/dwc2/dcd_dwc2.c \ - $(GD32VF103_SDK_DRIVER)/gd32vf103_rcu.c \ $(GD32VF103_SDK_DRIVER)/gd32vf103_gpio.c \ - $(GD32VF103_SDK_DRIVER)/Usb/gd32vf103_usb_hw.c \ + $(GD32VF103_SDK_DRIVER)/gd32vf103_rcu.c \ $(GD32VF103_SDK_DRIVER)/gd32vf103_usart.c \ + $(GD32VF103_SDK_DRIVER)/Usb/gd32vf103_usb_hw.c \ $(LIBC_STUBS)/sbrk.c \ $(LIBC_STUBS)/close.c \ $(LIBC_STUBS)/isatty.c \ diff --git a/hw/bsp/lpc51/family.cmake b/hw/bsp/lpc51/family.cmake index dd0ef6d1b..b9dd8829e 100644 --- a/hw/bsp/lpc51/family.cmake +++ b/hw/bsp/lpc51/family.cmake @@ -34,7 +34,6 @@ function(add_board_target BOARD_TARGET) add_library(${BOARD_TARGET} STATIC ${STARTUP_FILE_${CMAKE_C_COMPILER_ID}} # driver - ${SDK_DIR}/drivers/common/fsl_common_arm.c ${SDK_DIR}/drivers/lpc_gpio/fsl_gpio.c ${SDK_DIR}/drivers/flexcomm/fsl_flexcomm.c ${SDK_DIR}/drivers/flexcomm/fsl_usart.c diff --git a/src/device/usbd.c b/src/device/usbd.c index e51aa0fc4..6aeaa699f 100644 --- a/src/device/usbd.c +++ b/src/device/usbd.c @@ -90,16 +90,16 @@ tu_static usbd_device_t _usbd_dev; // Class Driver //--------------------------------------------------------------------+ #if CFG_TUSB_DEBUG >= CFG_TUD_LOG_LEVEL - #define DRIVER_NAME(_name) .name = _name, + #define DRIVER_NAME(_name) _name #else - #define DRIVER_NAME(_name) + #define DRIVER_NAME(_name) NULL #endif // Built-in class drivers tu_static usbd_class_driver_t const _usbd_driver[] = { #if CFG_TUD_CDC { - DRIVER_NAME("CDC") + .name = DRIVER_NAME("CDC"), .init = cdcd_init, .deinit = cdcd_deinit, .reset = cdcd_reset, @@ -112,7 +112,7 @@ tu_static usbd_class_driver_t const _usbd_driver[] = { #if CFG_TUD_MSC { - DRIVER_NAME("MSC") + .name = DRIVER_NAME("MSC"), .init = mscd_init, .deinit = NULL, .reset = mscd_reset, @@ -125,7 +125,7 @@ tu_static usbd_class_driver_t const _usbd_driver[] = { #if CFG_TUD_HID { - DRIVER_NAME("HID") + .name = DRIVER_NAME("HID"), .init = hidd_init, .deinit = hidd_deinit, .reset = hidd_reset, @@ -138,7 +138,7 @@ tu_static usbd_class_driver_t const _usbd_driver[] = { #if CFG_TUD_AUDIO { - DRIVER_NAME("AUDIO") + .name = DRIVER_NAME("AUDIO"), .init = audiod_init, .deinit = audiod_deinit, .reset = audiod_reset, @@ -151,7 +151,7 @@ tu_static usbd_class_driver_t const _usbd_driver[] = { #if CFG_TUD_VIDEO { - DRIVER_NAME("VIDEO") + .name = DRIVER_NAME("VIDEO"), .init = videod_init, .deinit = videod_deinit, .reset = videod_reset, @@ -164,7 +164,7 @@ tu_static usbd_class_driver_t const _usbd_driver[] = { #if CFG_TUD_MIDI { - DRIVER_NAME("MIDI") + .name = DRIVER_NAME("MIDI"), .init = midid_init, .deinit = midid_deinit, .open = midid_open, @@ -177,7 +177,7 @@ tu_static usbd_class_driver_t const _usbd_driver[] = { #if CFG_TUD_VENDOR { - DRIVER_NAME("VENDOR") + .name = DRIVER_NAME("VENDOR"), .init = vendord_init, .deinit = vendord_deinit, .reset = vendord_reset, @@ -190,7 +190,7 @@ tu_static usbd_class_driver_t const _usbd_driver[] = { #if CFG_TUD_USBTMC { - DRIVER_NAME("TMC") + .name = DRIVER_NAME("TMC"), .init = usbtmcd_init_cb, .deinit = usbtmcd_deinit, .reset = usbtmcd_reset_cb, @@ -203,7 +203,7 @@ tu_static usbd_class_driver_t const _usbd_driver[] = { #if CFG_TUD_DFU_RUNTIME { - DRIVER_NAME("DFU-RUNTIME") + .name = DRIVER_NAME("DFU-RUNTIME"), .init = dfu_rtd_init, .deinit = dfu_rtd_deinit, .reset = dfu_rtd_reset, @@ -216,7 +216,7 @@ tu_static usbd_class_driver_t const _usbd_driver[] = { #if CFG_TUD_DFU { - DRIVER_NAME("DFU") + .name = DRIVER_NAME("DFU"), .init = dfu_moded_init, .deinit = dfu_moded_deinit, .reset = dfu_moded_reset, @@ -229,7 +229,7 @@ tu_static usbd_class_driver_t const _usbd_driver[] = { #if CFG_TUD_ECM_RNDIS || CFG_TUD_NCM { - DRIVER_NAME("NET") + .name = DRIVER_NAME("NET"), .init = netd_init, .deinit = netd_deinit, .reset = netd_reset, @@ -242,7 +242,7 @@ tu_static usbd_class_driver_t const _usbd_driver[] = { #if CFG_TUD_BTH { - DRIVER_NAME("BTH") + .name = DRIVER_NAME("BTH"), .init = btd_init, .deinit = btd_deinit, .reset = btd_reset, diff --git a/src/device/usbd_pvt.h b/src/device/usbd_pvt.h index 47752f32c..7eb504246 100644 --- a/src/device/usbd_pvt.h +++ b/src/device/usbd_pvt.h @@ -23,8 +23,8 @@ * * This file is part of the TinyUSB stack. */ -#ifndef _TUSB_USBD_PVT_H_ -#define _TUSB_USBD_PVT_H_ +#ifndef TUSB_USBD_PVT_H_ +#define TUSB_USBD_PVT_H_ #include "osal/osal.h" #include "common/tusb_fifo.h" @@ -40,10 +40,7 @@ //--------------------------------------------------------------------+ typedef struct { - #if CFG_TUSB_DEBUG >= CFG_TUD_LOG_LEVEL char const* name; - #endif - void (* init ) (void); bool (* deinit ) (void); void (* reset ) (uint8_t rhport); diff --git a/test/hil/hfp.json b/test/hil/hfp.json new file mode 100644 index 000000000..e79a3cfc9 --- /dev/null +++ b/test/hil/hfp.json @@ -0,0 +1,25 @@ +{ + "boards": [ + { + "name": "stm32l412nucleo", + "uid": "41003B000E504E5457323020", + "flasher": "jlink", + "flasher_sn": "774470029", + "flasher_args": "-device STM32L412KB" + }, + { + "name": "stm32f746disco", + "uid": "210041000C51343237303334", + "flasher": "jlink", + "flasher_sn": "770935966", + "flasher_args": "-device STM32F746NG" + }, + { + "name": "lpcxpresso43s67", + "uid": "08F000044528BAAA8D858F58C50700F5", + "flasher": "jlink", + "flasher_sn": "728973776", + "flasher_args": "-device LPC43S67_M4" + } + ] +} diff --git a/test/hil/hil_hfp.json b/test/hil/hil_hfp.json deleted file mode 100644 index e79a3cfc9..000000000 --- a/test/hil/hil_hfp.json +++ /dev/null @@ -1,25 +0,0 @@ -{ - "boards": [ - { - "name": "stm32l412nucleo", - "uid": "41003B000E504E5457323020", - "flasher": "jlink", - "flasher_sn": "774470029", - "flasher_args": "-device STM32L412KB" - }, - { - "name": "stm32f746disco", - "uid": "210041000C51343237303334", - "flasher": "jlink", - "flasher_sn": "770935966", - "flasher_args": "-device STM32F746NG" - }, - { - "name": "lpcxpresso43s67", - "uid": "08F000044528BAAA8D858F58C50700F5", - "flasher": "jlink", - "flasher_sn": "728973776", - "flasher_args": "-device LPC43S67_M4" - } - ] -} diff --git a/test/hil/hil_pi4.json b/test/hil/hil_pi4.json deleted file mode 100644 index 8aff81910..000000000 --- a/test/hil/hil_pi4.json +++ /dev/null @@ -1,37 +0,0 @@ -{ - "boards": [ - { - "name": "raspberry_pi_pico", - "uid": "E6614C311B764A37", - "flasher": "openocd", - "flasher_sn": "E6614103E72C1D2F", - "flasher_args": "-f interface/cmsis-dap.cfg -f target/rp2040.cfg -c \"adapter speed 5000\"" - }, - { - "name": "espressif_s3_devkitm", - "uid": "84F703C084E4", - "tests": [ - "cdc_msc_freertos", "hid_composite_freertos" - ], - "flasher": "esptool", - "flasher_sn": "3ea619acd1cdeb11a0a0b806e93fd3f1", - "flasher_args": "-b 1500000" - }, - { - "name": "feather_nrf52840_express", - "uid": "1F0479CD0F764471", - "flasher": "jlink", - "flasher_sn": "000682804350", - "flasher_args": "-device nrf52840_xxaa" - }, - { - "name": "itsybitsy_m4", - "uid": "D784B28C5338533335202020FF044726", - "flasher": "bossac", - "flashser_vendor": "Adafruit Industries", - "flasher_product": "ItsyBitsy M4 Express", - "flasher_reset_pin": "2", - "flasher_args": "--offset 0x4000" - } - ] -} diff --git a/test/hil/hil_test.py b/test/hil/hil_test.py index 7f03ce43f..dffb81765 100644 --- a/test/hil/hil_test.py +++ b/test/hil/hil_test.py @@ -33,12 +33,14 @@ import serial import subprocess import json import glob +import platform # for RPI double reset -try: - import gpiozero -except ImportError: - pass +if platform.machine() == 'aarch64': + try: + import gpiozero + except ImportError: + pass ENUM_TIMEOUT = 10 @@ -111,27 +113,39 @@ def read_disk_file(id, fname): # ------------------------------------------------------------- # Flashing firmware # ------------------------------------------------------------- +def run_cmd(cmd): + # print(cmd) + r = subprocess.run(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT) + title = 'command error' + if r.returncode != 0: + # print build output if failed + if os.getenv('CI'): + print(f"::group::{title}") + print(r.stdout.decode("utf-8")) + print(f"::endgroup::") + else: + print(title) + print(r.stdout.decode("utf-8")) + return r + + def flash_jlink(board, firmware): - script = ['halt', 'r', f'loadfile {firmware}', 'r', 'go', 'exit'] + script = ['halt', 'r', f'loadfile {firmware}.elf', 'r', 'go', 'exit'] with open('flash.jlink', 'w') as f: f.writelines(f'{s}\n' for s in script) - ret = subprocess.run( - f'JLinkExe -USB {board["flasher_sn"]} {board["flasher_args"]} -if swd -JTAGConf -1,-1 -speed auto -NoGui 1 -ExitOnError 1 -CommandFile flash.jlink', - shell=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT) + ret = run_cmd(f'JLinkExe -USB {board["flasher_sn"]} {board["flasher_args"]} -if swd -JTAGConf -1,-1 -speed auto -NoGui 1 -ExitOnError 1 -CommandFile flash.jlink') os.remove('flash.jlink') return ret def flash_openocd(board, firmware): - ret = subprocess.run( - f'openocd -c "adapter serial {board["flasher_sn"]}" {board["flasher_args"]} -c "program {firmware} reset exit"', - shell=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT) + ret = run_cmd(f'openocd -c "adapter serial {board["flasher_sn"]}" {board["flasher_args"]} -c "program {firmware}.elf reset exit"') return ret def flash_esptool(board, firmware): port = get_serial_dev(board["flasher_sn"], None, None, 0) - dir = os.path.dirname(firmware) + dir = os.path.dirname(f'{firmware}.bin') with open(f'{dir}/config.env') as f: IDF_TARGET = json.load(f)['IDF_TARGET'] with open(f'{dir}/flash_args') as f: @@ -154,9 +168,11 @@ def doublereset_with_rpi_gpio(board): time.sleep(0.1) led.on() + def flash_bossac(board, firmware): # double reset to enter bootloader - doublereset_with_rpi_gpio(board) + if platform.machine() == 'aarch64': + doublereset_with_rpi_gpio(board) port = get_serial_dev(board["uid"], board["flashser_vendor"], board["flasher_product"], 0) timeout = ENUM_TIMEOUT @@ -169,8 +185,7 @@ def flash_bossac(board, firmware): assert timeout, 'bossac bootloader is not available' # sleep a bit more for bootloader to be ready time.sleep(0.5) - ret = subprocess.run(f'bossac --port {port} {board["flasher_args"]} -U -i -R -e -w {firmware}', shell=True, stdout=subprocess.PIPE, - stderr=subprocess.STDOUT) + ret = run_cmd(f'bossac --port {port} {board["flasher_args"]} -U -i -R -e -w {firmware}.bin') return ret # ------------------------------------------------------------- @@ -325,7 +340,8 @@ def main(config_file, board): config_boards = [e for e in config['boards'] if e['name'] in board] for item in config_boards: - print(f'Testing board:{item["name"]}') + name = item['name'] + print(f'Testing board:{name}') flasher = item['flasher'].lower() # default to all tests @@ -344,29 +360,12 @@ def main(config_file, board): test_list.remove(skip) for test in test_list: - fw_list = [ - # cmake: esp32 & samd51 use .bin file - f'cmake-build/cmake-build-{item["name"]}/device/{test}/{test}.elf', - f'cmake-build/cmake-build-{item["name"]}/device/{test}/{test}.bin', - # make - f'examples/device/{test}/_build/{item["name"]}/{test}.elf' - ] - - fw = None - for f in fw_list: - if os.path.isfile(f): - fw = f - break - - if fw is None: - print(f'Cannot find binary file for {test}') - sys.exit(-1) - + fw_name = f'cmake-build/cmake-build-{name}/device/{test}/{test}' print(f' {test} ...', end='') # flash firmware. It may fail randomly, retry a few times for i in range(3): - ret = globals()[f'flash_{flasher}'](item, fw) + ret = globals()[f'flash_{flasher}'](item, fw_name) if ret.returncode == 0: break else: diff --git a/test/hil/pi4.json b/test/hil/pi4.json new file mode 100644 index 000000000..04329bb64 --- /dev/null +++ b/test/hil/pi4.json @@ -0,0 +1,27 @@ +{ + "boards": [ + { + "name": "raspberry_pi_pico", + "uid": "E6614C311B764A37", + "flasher": "openocd", + "flasher_sn": "E6614103E72C1D2F", + "flasher_args": "-f interface/cmsis-dap.cfg -f target/rp2040.cfg -c \"adapter speed 5000\"" + }, + { + "name": "feather_nrf52840_express", + "uid": "1F0479CD0F764471", + "flasher": "jlink", + "flasher_sn": "000682804350", + "flasher_args": "-device nrf52840_xxaa" + }, + { + "name": "itsybitsy_m4", + "uid": "D784B28C5338533335202020FF044726", + "flasher": "bossac", + "flashser_vendor": "Adafruit Industries", + "flasher_product": "ItsyBitsy M4 Express", + "flasher_reset_pin": "2", + "flasher_args": "--offset 0x4000" + } + ] +} diff --git a/test/hil/pi4_esp32.json b/test/hil/pi4_esp32.json new file mode 100644 index 000000000..c95dd2d4e --- /dev/null +++ b/test/hil/pi4_esp32.json @@ -0,0 +1,14 @@ +{ + "boards": [ + { + "name": "espressif_s3_devkitm", + "uid": "84F703C084E4", + "tests": [ + "cdc_msc_freertos", "hid_composite_freertos" + ], + "flasher": "esptool", + "flasher_sn": "3ea619acd1cdeb11a0a0b806e93fd3f1", + "flasher_args": "-b 1500000" + } + ] +} diff --git a/tools/build.py b/tools/build.py new file mode 100644 index 000000000..884cd56f4 --- /dev/null +++ b/tools/build.py @@ -0,0 +1,177 @@ +import os +import sys +import time +import subprocess +import click +from pathlib import Path +from multiprocessing import Pool + +import build_utils + +SUCCEEDED = "\033[32msucceeded\033[0m" +FAILED = "\033[31mfailed\033[0m" + +build_separator = '-' * 106 + + +def run_cmd(cmd): + #print(cmd) + r = subprocess.run(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT) + title = 'command error' + if r.returncode != 0: + # print build output if failed + if os.getenv('CI'): + print(f"::group::{title}") + print(r.stdout.decode("utf-8")) + print(f"::endgroup::") + else: + print(title) + print(r.stdout.decode("utf-8")) + return r + +def find_family(board): + bsp_dir = Path("hw/bsp") + for family_dir in bsp_dir.iterdir(): + if family_dir.is_dir(): + board_dir = family_dir / 'boards' / board + if board_dir.exists(): + return family_dir.name + return None + + +def get_examples(family): + all_examples = [] + for d in os.scandir("examples"): + if d.is_dir() and 'cmake' not in d.name and 'build_system' not in d.name: + for entry in os.scandir(d.path): + if entry.is_dir() and 'cmake' not in entry.name: + if family != 'espressif' or 'freertos' in entry.name: + all_examples.append(d.name + '/' + entry.name) + + if family == 'espressif': + all_examples.append('device/board_test') + all_examples.append('device/video_capture') + all_examples.sort() + return all_examples + + +def build_board_cmake(board, toolchain): + start_time = time.monotonic() + ret = [0, 0, 0] + + build_dir = f"cmake-build/cmake-build-{board}" + family = find_family(board) + if family == 'espressif': + # for espressif, we have to build example individually + all_examples = get_examples(family) + for example in all_examples: + r = run_cmd(f'cmake examples/{example} -B {build_dir}/{example} -G "Ninja" -DBOARD={board} -DMAX3421_HOST=1') + if r.returncode == 0: + r = run_cmd(f'cmake --build {build_dir}/{example}') + if r.returncode == 0: + ret[0] += 1 + else: + ret[1] += 1 + else: + r = run_cmd(f'cmake examples -B {build_dir} -G "Ninja" -DBOARD={board} -DCMAKE_BUILD_TYPE=MinSizeRel -DTOOLCHAIN={toolchain}') + if r.returncode == 0: + r = run_cmd(f"cmake --build {build_dir}") + if r.returncode == 0: + ret[0] += 1 + else: + ret[1] += 1 + + duration = time.monotonic() - start_time + + if ret[1] == 0: + status = SUCCEEDED + else: + status = FAILED + + flash_size = "-" + sram_size = "-" + example = 'all' + title = build_utils.build_format.format(example, board, status, "{:.2f}s".format(duration), flash_size, sram_size) + print(title) + return ret + + +def build_family(family, toolchain, build_system): + all_boards = [] + for entry in os.scandir(f"hw/bsp/{family}/boards"): + if entry.is_dir() and entry.name != 'pico_sdk': + all_boards.append(entry.name) + all_boards.sort() + + # success, failed, skipped + ret = [0, 0, 0] + if build_system == 'cmake': + for board in all_boards: + if build_board_cmake(board, toolchain): + ret[0] += 1 + else: + ret[1] += 1 + elif build_system == 'make': + all_examples = get_examples(family) + for example in all_examples: + with Pool(processes=os.cpu_count()) as pool: + pool_args = list((map(lambda b, e=example, o=f"TOOLCHAIN={toolchain}": [e, b, o], all_boards))) + r = pool.starmap(build_utils.build_example, pool_args) + # sum all element of same index (column sum) + rsum = list(map(sum, list(zip(*r)))) + ret[0] += rsum[0] + ret[1] += rsum[1] + ret[2] += rsum[2] + return ret + + +@click.command() +@click.argument('families', nargs=-1, required=False) +@click.option('-b', '--board', multiple=True, default=None, help='Boards to build') +@click.option('-t', '--toolchain', default='gcc', help='Toolchain to use, default is gcc') +@click.option('-s', '--build-system', default='cmake', help='Build system to use, default is cmake') +def main(families, board, toolchain, build_system): + if len(families) == 0 and len(board) == 0: + print("Please specify families or board to build") + return 1 + + print(build_separator) + print(build_utils.build_format.format('Example', 'Board', '\033[39mResult\033[0m', 'Time', 'Flash', 'SRAM')) + total_time = time.monotonic() + total_result = [0, 0, 0] + + # build families: cmake, make + if families is not None: + all_families = [] + if 'all' in families: + for entry in os.scandir("hw/bsp"): + if entry.is_dir() and entry.name != 'espressif' and os.path.isfile(entry.path + "/family.cmake"): + all_families.append(entry.name) + else: + all_families = list(families) + all_families.sort() + + # succeeded, failed + for f in all_families: + fret = build_family(f, toolchain, build_system) + total_result[0] += fret[0] + total_result[1] += fret[1] + total_result[2] += fret[2] + + # build board (only cmake) + if board is not None: + for b in board: + r = build_board_cmake(b, toolchain) + total_result[0] += r[0] + total_result[1] += r[1] + total_result[2] += r[2] + + total_time = time.monotonic() - total_time + print(build_separator) + print(f"Build Summary: {total_result[0]} {SUCCEEDED}, {total_result[1]} {FAILED} and took {total_time:.2f}s") + print(build_separator) + return total_result[1] + + +if __name__ == '__main__': + sys.exit(main()) diff --git a/tools/build_board.py b/tools/build_board.py deleted file mode 100644 index 13376d126..000000000 --- a/tools/build_board.py +++ /dev/null @@ -1,69 +0,0 @@ -import os -import sys -import time -import subprocess -from multiprocessing import Pool - -import build_utils - -SUCCEEDED = "\033[32msucceeded\033[0m" -FAILED = "\033[31mfailed\033[0m" -SKIPPED = "\033[33mskipped\033[0m" - -build_separator = '-' * 106 - - -def filter_with_input(mylist): - if len(sys.argv) > 1: - input_args = list(set(mylist).intersection(sys.argv)) - if len(input_args) > 0: - mylist[:] = input_args - - -if __name__ == '__main__': - # If examples are not specified in arguments, build all - all_examples = [] - for dir1 in os.scandir("examples"): - if dir1.is_dir(): - for entry in os.scandir(dir1.path): - if entry.is_dir(): - all_examples.append(dir1.name + '/' + entry.name) - filter_with_input(all_examples) - all_examples.sort() - - # If boards are not specified in arguments, build all - all_boards = [] - for entry in os.scandir("hw/bsp"): - if entry.is_dir() and os.path.exists(entry.path + "/board.mk"): - all_boards.append(entry.name) - filter_with_input(all_boards) - all_boards.sort() - - # Get dependencies - for b in all_boards: - subprocess.run("make -C examples/device/board_test BOARD={} get-deps".format(b), shell=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT) - - print(build_separator) - print(build_utils.build_format.format('Example', 'Board', '\033[39mResult\033[0m', 'Time', 'Flash', 'SRAM')) - total_time = time.monotonic() - - # succeeded, failed, skipped - total_result = [0, 0, 0] - for example in all_examples: - print(build_separator) - with Pool(processes=os.cpu_count()) as pool: - pool_args = list((map(lambda b, e=example, o='': [e, b, o], all_boards))) - result = pool.starmap(build_utils.build_example, pool_args) - # sum all element of same index (column sum) - result = list(map(sum, list(zip(*result)))) - - # add to total result - total_result = list(map(lambda x, y: x + y, total_result, result)) - - total_time = time.monotonic() - total_time - print(build_separator) - print("Build Summary: {} {}, {} {}, {} {} and took {:.2f}s".format(total_result[0], SUCCEEDED, total_result[1], - FAILED, total_result[2], SKIPPED, total_time)) - print(build_separator) - - sys.exit(total_result[1]) diff --git a/tools/build_cmake.py b/tools/build_cmake.py deleted file mode 100644 index 2eda3f90f..000000000 --- a/tools/build_cmake.py +++ /dev/null @@ -1,105 +0,0 @@ -import os -import sys -import time -import subprocess -import pathlib -from multiprocessing import Pool - -import build_utils - -SUCCEEDED = "\033[32msucceeded\033[0m" -FAILED = "\033[31mfailed\033[0m" -SKIPPED = "\033[33mskipped\033[0m" - -build_separator = '-' * 106 - -def filter_with_input(mylist): - if len(sys.argv) > 1: - input_args = list(set(mylist).intersection(sys.argv)) - if len(input_args) > 0: - mylist[:] = input_args - - -def build_family(family, cmake_option): - all_boards = [] - for entry in os.scandir("hw/bsp/{}/boards".format(family)): - if entry.is_dir() and entry.name != 'pico_sdk': - all_boards.append(entry.name) - all_boards.sort() - - # success, failed, skipped - ret = [0, 0, 0] - for board in all_boards: - start_time = time.monotonic() - - build_dir = f"cmake-build/cmake-build-{board}" - - # Generate build - r = subprocess.run(f"cmake examples -B {build_dir} -G \"Ninja\" -DFAMILY={family} -DBOARD" - f"={board} -DCMAKE_BUILD_TYPE=MinSizeRel {cmake_option}", shell=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT) - - # Build - if r.returncode == 0: - r = subprocess.run(f"cmake --build {build_dir}", shell=True, stdout=subprocess.PIPE, - stderr=subprocess.STDOUT) - - duration = time.monotonic() - start_time - - if r.returncode == 0: - status = SUCCEEDED - ret[0] += 1 - else: - status = FAILED - ret[1] += 1 - - flash_size = "-" - sram_size = "-" - example = 'all' - title = build_utils.build_format.format(example, board, status, "{:.2f}s".format(duration), flash_size, sram_size) - - if os.getenv('CI'): - # always print build output if in CI - print(f"::group::{title}") - print(r.stdout.decode("utf-8")) - print(f"::endgroup::") - else: - # print build output if failed - print(title) - if r.returncode != 0: - print(r.stdout.decode("utf-8")) - - return ret - - -if __name__ == '__main__': - cmake_options = '' - for a in sys.argv[1:]: - if a.startswith('-'): - cmake_options += ' ' + a - - # If family are not specified in arguments, build all supported - all_families = [] - for entry in os.scandir("hw/bsp"): - if entry.is_dir() and entry.name != 'espressif' and os.path.isfile(entry.path + "/family.cmake"): - all_families.append(entry.name) - filter_with_input(all_families) - all_families.sort() - - print(build_separator) - print(build_utils.build_format.format('Example', 'Board', '\033[39mResult\033[0m', 'Time', 'Flash', 'SRAM')) - total_time = time.monotonic() - - # succeeded, failed, skipped - total_result = [0, 0, 0] - for family in all_families: - fret = build_family(family, cmake_options) - if len(fret) == len(total_result): - total_result = [total_result[i] + fret[i] for i in range(len(fret))] - - total_time = time.monotonic() - total_time - print(build_separator) - print("Build Summary: {} {}, {} {}, {} {} and took {:.2f}s".format(total_result[0], SUCCEEDED, total_result[1], - FAILED, total_result[2], SKIPPED, total_time)) - print(build_separator) - - sys.exit(total_result[1]) diff --git a/tools/build_make.py b/tools/build_make.py deleted file mode 100644 index 240fc8d64..000000000 --- a/tools/build_make.py +++ /dev/null @@ -1,80 +0,0 @@ -import os -import sys -import time -from multiprocessing import Pool - -import build_utils - -SUCCEEDED = "\033[32msucceeded\033[0m" -FAILED = "\033[31mfailed\033[0m" -SKIPPED = "\033[33mskipped\033[0m" - -build_separator = '-' * 106 - - -def filter_with_input(mylist): - if len(sys.argv) > 1: - input_args = list(set(mylist).intersection(sys.argv)) - if len(input_args) > 0: - mylist[:] = input_args - - -def build_family(example, family, make_option): - all_boards = [] - for entry in os.scandir("hw/bsp/{}/boards".format(family)): - if entry.is_dir() and entry.name != 'pico_sdk': - all_boards.append(entry.name) - filter_with_input(all_boards) - all_boards.sort() - - with Pool(processes=os.cpu_count()) as pool: - pool_args = list((map(lambda b, e=example, o=make_option: [e, b, o], all_boards))) - result = pool.starmap(build_utils.build_example, pool_args) - # sum all element of same index (column sum) - return list(map(sum, list(zip(*result)))) - - -if __name__ == '__main__': - make_option = '' - for a in sys.argv: - if 'TOOLCHAIN=' in sys.argv: - make_option += ' ' + a - - # If examples are not specified in arguments, build all - all_examples = [] - for d in os.scandir("examples"): - if d.is_dir() and 'cmake' not in d.name and 'build_system' not in d.name: - for entry in os.scandir(d.path): - if entry.is_dir() and 'cmake' not in entry.name: - all_examples.append(d.name + '/' + entry.name) - filter_with_input(all_examples) - all_examples.sort() - - # If family are not specified in arguments, build all - all_families = [] - for entry in os.scandir("hw/bsp"): - if entry.is_dir() and os.path.isdir(entry.path + "/boards") and entry.name != 'espressif': - all_families.append(entry.name) - filter_with_input(all_families) - all_families.sort() - - print(build_separator) - print(build_utils.build_format.format('Example', 'Board', '\033[39mResult\033[0m', 'Time', 'Flash', 'SRAM')) - total_time = time.monotonic() - - # succeeded, failed, skipped - total_result = [0, 0, 0] - for example in all_examples: - print(build_separator) - for family in all_families: - fret = build_family(example, family, make_option) - if len(fret) == len(total_result): - total_result = [total_result[i] + fret[i] for i in range(len(fret))] - - total_time = time.monotonic() - total_time - print(build_separator) - print("Build Summary: {} {}, {} {}, {} {} and took {:.2f}s".format(total_result[0], SUCCEEDED, total_result[1], - FAILED, total_result[2], SKIPPED, total_time)) - print(build_separator) - - sys.exit(total_result[1]) diff --git a/tools/get_deps.py b/tools/get_deps.py index cdb5dafe1..bca38fc80 100644 --- a/tools/get_deps.py +++ b/tools/get_deps.py @@ -1,3 +1,4 @@ +import click import sys import subprocess from pathlib import Path @@ -227,27 +228,46 @@ def get_a_dep(d): return 0 -# Arguments can be -# - family name -# - specific deps path -# - all -if __name__ == "__main__": +def find_family(board): + bsp_dir = Path(TOP / "hw/bsp") + for family_dir in bsp_dir.iterdir(): + if family_dir.is_dir(): + board_dir = family_dir / 'boards' / board + if board_dir.exists(): + return family_dir.name + return None + + +@click.command() +@click.argument('family', nargs=-1, required=False) +@click.option('-b', '--board', multiple=True, default=None, help='Boards to fetch') +def main(family, board): + if len(family) == 0 and len(board) == 0: + print("Please specify family or board to fetch") + return + status = 0 deps = list(deps_mandatory.keys()) - # get all if 'all' is argument - if len(sys.argv) == 2 and sys.argv[1] == 'all': + + if 'all' in family: deps += deps_optional.keys() else: - for arg in sys.argv[1:]: - if arg in deps_all.keys(): - # if arg is a dep, add it - deps.append(arg) - else: - # arg is a family name, add all deps of that family - for d in deps_optional: - if arg in deps_optional[d][2]: - deps.append(d) + family = list(family) + if board is not None: + for b in board: + f = find_family(b) + if f is not None: + family.append(f) + + for f in family: + for d in deps_optional: + if f in deps_optional[d][2]: + deps.append(d) with Pool() as pool: status = sum(pool.map(get_a_dep, deps)) - sys.exit(status) + return status + + +if __name__ == "__main__": + sys.exit(main()) -- cgit v1.3.1 From 3e2ea7750681b27238043c7158ff5508f01914a3 Mon Sep 17 00:00:00 2001 From: Ha Thach Date: Fri, 10 May 2024 18:55:43 +0700 Subject: More ci tweak (#2636) * change concurrency group to ${{ github.workflow }}-${{ github.ref }} * use argparse for build.py hil_test.py, remove the need to install click * move ci win/mac to build_cmake.yml * rename build_family.yml to build_util.yml * build_util.yml support esp32 * integrate build-espressif into build.yml * build.py support make with --board option * add get_deps action * update hil test to reuse action --- .github/actions/get_deps/action.yml | 29 +++++++ .github/actions/prepare_build/action.yml | 30 ------- .github/actions/setup_toolchain/action.yml | 18 ++++- .github/workflows/build_cmake.yml | 46 +++++++++-- .github/workflows/build_esp.yml | 109 ------------------------- .github/workflows/build_family.yml | 64 --------------- .github/workflows/build_iar.yml | 2 +- .github/workflows/build_renesas.yml | 3 +- .github/workflows/build_util.yml | 59 ++++++++++++++ .github/workflows/build_win_mac.yml | 56 ------------- .github/workflows/ci_set_matrix.py | 2 +- .github/workflows/hil_test.yml | 121 ++++++++++++++++++++-------- .github/workflows/pre-commit.yml | 3 +- examples/device/net_lwip_webserver/skip.txt | 4 +- examples/device/video_capture_2ch/skip.txt | 2 + examples/host/cdc_msc_hid_freertos/only.txt | 1 - hw/bsp/lpc17/family.mk | 2 +- hw/bsp/lpc40/family.mk | 2 + src/class/net/ncm_device.c | 16 ++-- test/hil/hil_test.py | 19 +++-- test/hil/pi4.json | 10 +++ test/hil/pi4_esp32.json | 14 ---- tools/build.py | 46 +++++++---- tools/build_esp32.py | 106 ------------------------ tools/get_deps.py | 11 ++- 25 files changed, 314 insertions(+), 461 deletions(-) create mode 100644 .github/actions/get_deps/action.yml delete mode 100644 .github/actions/prepare_build/action.yml delete mode 100644 .github/workflows/build_esp.yml delete mode 100644 .github/workflows/build_family.yml create mode 100644 .github/workflows/build_util.yml delete mode 100644 .github/workflows/build_win_mac.yml delete mode 100644 test/hil/pi4_esp32.json delete mode 100644 tools/build_esp32.py (limited to '.github/workflows/pre-commit.yml') diff --git a/.github/actions/get_deps/action.yml b/.github/actions/get_deps/action.yml new file mode 100644 index 000000000..38b44a70e --- /dev/null +++ b/.github/actions/get_deps/action.yml @@ -0,0 +1,29 @@ +name: Get dependencies + +inputs: + arg: + required: true + type: string + +runs: + using: "composite" + steps: + - name: Checkout pico-sdk for rp2040 + if: contains(inputs.arg, 'rp2040') || contains(inputs.arg, 'raspberry_pi_pico') + uses: actions/checkout@v4 + with: + repository: raspberrypi/pico-sdk + ref: develop + path: pico-sdk + + - name: Linux dependencies + if: runner.os == 'Linux' + run: | + sudo apt install -y ninja-build + shell: bash + + - name: Get Dependencies + run: | + python3 tools/get_deps.py ${{ inputs.arg }} + echo "PICO_SDK_PATH=${{ github.workspace }}/pico-sdk" >> $GITHUB_ENV + shell: bash diff --git a/.github/actions/prepare_build/action.yml b/.github/actions/prepare_build/action.yml deleted file mode 100644 index 5f2c544c1..000000000 --- a/.github/actions/prepare_build/action.yml +++ /dev/null @@ -1,30 +0,0 @@ -name: Prepare to build - -inputs: - family: - required: true - type: string - -runs: - using: "composite" - steps: - - name: Setup Python - uses: actions/setup-python@v5 - with: - python-version: '3.x' - - - name: Checkout pico-sdk for rp2040 - if: contains(inputs.family, 'rp2040') - uses: actions/checkout@v4 - with: - repository: raspberrypi/pico-sdk - ref: develop - path: pico-sdk - - - name: Get Dependencies - run: | - sudo apt install -y ninja-build - pip install click - python3 tools/get_deps.py ${{ inputs.family }} - echo >> $GITHUB_ENV "PICO_SDK_PATH=$GITHUB_WORKSPACE/pico-sdk" - shell: bash diff --git a/.github/actions/setup_toolchain/action.yml b/.github/actions/setup_toolchain/action.yml index b59ece116..e6c79e7dd 100644 --- a/.github/actions/setup_toolchain/action.yml +++ b/.github/actions/setup_toolchain/action.yml @@ -8,6 +8,11 @@ inputs: required: false type: string +outputs: + build_option: + description: 'Build option for the toolchain e.g --toolchain clang' + value: ${{ steps.set-toolchain-option.outputs.build_option }} + runs: using: "composite" steps: @@ -19,7 +24,7 @@ runs: - name: Pull ESP-IDF docker if: inputs.toolchain == 'esp-idf' - run: docker pull espressif/idf:latest + run: docker pull espressif/idf:${{ inputs.toolchain_url }} shell: bash - name: Download Toolchain @@ -29,3 +34,14 @@ runs: uses: ./.github/actions/setup_toolchain/download with: toolchain_url: ${{ inputs.toolchain_url }} + + - name: Set toolchain option + id: set-toolchain-option + run: | + BUILD_OPTION="" + if [[ "${{ inputs.toolchain }}" == *"clang"* ]]; then + BUILD_OPTION="--toolchain clang" + fi + echo "build_option=$BUILD_OPTION" + echo "build_option=$BUILD_OPTION" >> $GITHUB_OUTPUT + shell: bash diff --git a/.github/workflows/build_cmake.yml b/.github/workflows/build_cmake.yml index b62a0e9bd..4723cf8d9 100644 --- a/.github/workflows/build_cmake.yml +++ b/.github/workflows/build_cmake.yml @@ -12,6 +12,7 @@ on: - 'tools/build.py' - '.github/actions/**' - '.github/workflows/build_cmake.yml' + - '.github/workflows/build_util.yml' - '.github/workflows/ci_set_matrix.py' pull_request: branches: [ master ] @@ -24,9 +25,10 @@ on: - 'tools/build.py' - '.github/actions/**' - '.github/workflows/build_cmake.yml' + - '.github/workflows/build_util.yml' - '.github/workflows/ci_set_matrix.py' concurrency: - group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} + group: ${{ github.workflow }}-${{ github.ref }} cancel-in-progress: true jobs: @@ -55,7 +57,7 @@ jobs: # --------------------------------------- cmake: needs: set-matrix - uses: ./.github/workflows/build_family.yml + uses: ./.github/workflows/build_util.yml strategy: fail-fast: false matrix: @@ -69,14 +71,14 @@ jobs: build-system: 'cmake' toolchain: ${{ matrix.toolchain }} toolchain_url: ${{ fromJSON(needs.set-matrix.outputs.json)[matrix.toolchain].toolchain_url }} - build-family: ${{ toJSON(fromJSON(needs.set-matrix.outputs.json)[matrix.toolchain].family) }} + build-args: ${{ toJSON(fromJSON(needs.set-matrix.outputs.json)[matrix.toolchain].family) }} # --------------------------------------- # Build Make # --------------------------------------- make: needs: set-matrix - uses: ./.github/workflows/build_family.yml + uses: ./.github/workflows/build_util.yml strategy: fail-fast: false matrix: @@ -90,4 +92,38 @@ jobs: build-system: 'make' toolchain: ${{ matrix.toolchain }} toolchain_url: ${{ fromJSON(needs.set-matrix.outputs.json)[matrix.toolchain].toolchain_url }} - build-family: ${{ toJSON(fromJSON(needs.set-matrix.outputs.json)[matrix.toolchain].family) }} + build-args: ${{ toJSON(fromJSON(needs.set-matrix.outputs.json)[matrix.toolchain].family) }} + + # --------------------------------------- + # Build Make on Windows/MacOS + # --------------------------------------- + make-os: + uses: ./.github/workflows/build_util.yml + strategy: + fail-fast: false + matrix: + os: [windows-latest, macos-latest] + with: + os: ${{ matrix.os }} + build-system: 'make' + toolchain: 'arm-gcc' + build-args: '["-bstm32f411disco"]' + + # --------------------------------------- + # Build Espressif + # --------------------------------------- + espressif: + uses: ./.github/workflows/build_util.yml + strategy: + fail-fast: false + matrix: + board: + # ESP32-S2 + - 'espressif_kaluga_1' + # ESP32-S3 skip since devkitm is also compiled in hil-test workflow + #- 'espressif_s3_devkitm' + with: + build-system: 'cmake' + toolchain: 'esp-idf' + toolchain_url: 'v5.1.1' + build-args: '["-b${{ matrix.board }}"]' diff --git a/.github/workflows/build_esp.yml b/.github/workflows/build_esp.yml deleted file mode 100644 index 66fa8548e..000000000 --- a/.github/workflows/build_esp.yml +++ /dev/null @@ -1,109 +0,0 @@ -name: Build ESP - -on: - workflow_dispatch: - push: - paths: - - 'src/**' - - 'examples/**' - - 'lib/**' - - 'hw/**' - - 'test/hil/**' - - '.github/workflows/build_esp.yml' - pull_request: - branches: [ master ] - paths: - - 'src/**' - - 'examples/**' - - 'lib/**' - - 'hw/**' - - 'test/hil/**' - - '.github/workflows/build_esp.yml' - -concurrency: - group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} - cancel-in-progress: true - -jobs: - build-esp: - runs-on: ubuntu-latest - strategy: - fail-fast: false - matrix: - board: - # ESP32-S2 - - 'espressif_kaluga_1' - # ESP32-S3 - - 'espressif_s3_devkitm' - steps: - - name: Setup Python - uses: actions/setup-python@v5 - with: - python-version: '3.x' - - - name: Checkout TinyUSB - uses: actions/checkout@v4 - - - name: Setup Toolchain - uses: ./.github/actions/setup_toolchain - with: - toolchain: 'esp-idf' - - - name: Build - run: docker run --rm -v $PWD:/project -w /project espressif/idf:v5.1.1 python3 tools/build.py -b ${{ matrix.board }} - - - name: Upload Artifacts for Hardware Testing - if: matrix.board == 'espressif_s3_devkitm' && github.repository_owner == 'hathach' - uses: actions/upload-artifact@v4 - with: - name: ${{ matrix.board }} - path: | - cmake-build/cmake-build-${{ matrix.board }}/*/*/bootloader/bootloader.bin - cmake-build/cmake-build-${{ matrix.board }}/*/*/*.bin - cmake-build/cmake-build-${{ matrix.board }}/*/*/partition_table/partition-table.bin - cmake-build/cmake-build-${{ matrix.board }}/*/*/config.env - cmake-build/cmake-build-${{ matrix.board }}/*/*/flash_args - - # --------------------------------------- - # Hardware in the loop (HIL) - # Current self-hosted instance is running on an RPI4. For attached hardware checkout hil_pi4.json - # --------------------------------------- - hil-test: - # run only with hathach's commit due to limited resource on RPI4 - if: github.repository_owner == 'hathach' - needs: build-esp - runs-on: [self-hosted, esp32s3, hardware-in-the-loop] - strategy: - fail-fast: false - matrix: - board: - - 'espressif_s3_devkitm' - steps: - - name: Clean workspace - run: | - echo "Cleaning up previous run" - rm -rf "${{ github.workspace }}" - mkdir -p "${{ github.workspace }}" - - # USB bus on rpi4 is not stable, reset it before testing - - name: Reset USB bus - run: | - lsusb - lsusb -t - # reset VIA Labs 2.0 hub - sudo usbreset 001/002 - - - name: Checkout test/hil - uses: actions/checkout@v4 - with: - sparse-checkout: test/hil - - - name: Download Artifacts - uses: actions/download-artifact@v4 - with: - name: ${{ matrix.board }} - path: cmake-build/cmake-build-${{ matrix.board }} - - - name: Test on actual hardware - run: | - python3 test/hil/hil_test.py --board ${{ matrix.board }} pi4_esp32.json diff --git a/.github/workflows/build_family.yml b/.github/workflows/build_family.yml deleted file mode 100644 index 2e89267a3..000000000 --- a/.github/workflows/build_family.yml +++ /dev/null @@ -1,64 +0,0 @@ -name: Build family - -on: - workflow_call: - inputs: - build-system: - required: true - type: string - toolchain: - required: true - type: string - toolchain_url: - required: true - type: string - build-family: - required: true - type: string - -jobs: - family: - runs-on: ubuntu-latest - strategy: - fail-fast: false - matrix: - family: ${{ fromJSON(inputs.build-family) }} - steps: - - name: Checkout TinyUSB - uses: actions/checkout@v4 - - - name: Setup Python - uses: actions/setup-python@v5 - with: - python-version: '3.x' - - - name: Setup Toolchain - uses: ./.github/actions/setup_toolchain - with: - toolchain: ${{ inputs.toolchain }} - toolchain_url: ${{ inputs.toolchain_url }} - - - name: Checkout pico-sdk for rp2040 - if: contains(matrix.family, 'rp2040') - uses: actions/checkout@v4 - with: - repository: raspberrypi/pico-sdk - ref: develop - path: pico-sdk - - - name: Get Dependencies - run: | - sudo apt install -y ninja-build - pip install click - python3 tools/get_deps.py ${{ matrix.family }} - - - name: Build - run: | - OPTION="" - if [[ "${{ inputs.toolchain }}" == *"clang"* ]]; then - OPTION="--toolchain clang" - fi - echo "OPTION=$OPTION" - python tools/build.py -s ${{ inputs.build-system }} $OPTION ${{ matrix.family }} - env: - PICO_SDK_PATH: ${{ github.workspace }}/pico-sdk diff --git a/.github/workflows/build_iar.yml b/.github/workflows/build_iar.yml index c4a7f96b7..34dbda192 100644 --- a/.github/workflows/build_iar.yml +++ b/.github/workflows/build_iar.yml @@ -23,7 +23,7 @@ on: - '.github/workflows/build_iar.yml' concurrency: - group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} + group: ${{ github.workflow }}-${{ github.ref }} cancel-in-progress: true jobs: diff --git a/.github/workflows/build_renesas.yml b/.github/workflows/build_renesas.yml index 8c83bdbbf..1be49344f 100644 --- a/.github/workflows/build_renesas.yml +++ b/.github/workflows/build_renesas.yml @@ -21,7 +21,7 @@ on: - '.github/workflows/build_renesas.yml' concurrency: - group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} + group: ${{ github.workflow }}-${{ github.ref }} cancel-in-progress: true jobs: @@ -65,7 +65,6 @@ jobs: - name: Get Dependencies run: | - pip install click python3 tools/get_deps.py ${{ matrix.family }} - name: Build diff --git a/.github/workflows/build_util.yml b/.github/workflows/build_util.yml new file mode 100644 index 000000000..f8ad1900c --- /dev/null +++ b/.github/workflows/build_util.yml @@ -0,0 +1,59 @@ +name: Reusable build util + +on: + workflow_call: + inputs: + build-system: + required: true + type: string + toolchain: + required: true + type: string + toolchain_url: + required: false + type: string + build-args: + required: true + type: string + os: + required: false + type: string + default: 'ubuntu-latest' + +jobs: + family: + runs-on: ${{ inputs.os }} + strategy: + fail-fast: false + matrix: + arg: ${{ fromJSON(inputs.build-args) }} + steps: + - name: Checkout TinyUSB + uses: actions/checkout@v4 + + - name: Setup Python + uses: actions/setup-python@v5 + with: + python-version: '3.x' + + - name: Setup Toolchain + id: setup-toolchain + uses: ./.github/actions/setup_toolchain + with: + toolchain: ${{ inputs.toolchain }} + toolchain_url: ${{ inputs.toolchain_url }} + + - name: Get Dependencies + uses: ./.github/actions/get_deps + with: + arg: ${{ matrix.arg }} + + - name: Build + if: inputs.toolchain != 'esp-idf' + run: | + python tools/build.py -s ${{ inputs.build-system }} ${{ steps.setup-toolchain.outputs.build_option }} ${{ matrix.arg }} + + - name: Build using ESP-IDF docker + if: inputs.toolchain == 'esp-idf' + run: | + docker run --rm -v $PWD:/project -w /project espressif/idf:${{ inputs.toolchain_url }} python3 tools/build.py ${{ matrix.arg }} diff --git a/.github/workflows/build_win_mac.yml b/.github/workflows/build_win_mac.yml deleted file mode 100644 index 35328aa32..000000000 --- a/.github/workflows/build_win_mac.yml +++ /dev/null @@ -1,56 +0,0 @@ -name: Build Windows/MacOS - -on: - workflow_dispatch: - push: - paths: - - 'src/**' - - 'examples/**' - - 'lib/**' - - 'hw/**' - - '.github/workflows/build_win_mac.yml' - pull_request: - branches: [ master ] - paths: - - 'src/**' - - 'examples/**' - - 'lib/**' - - 'hw/**' - - '.github/workflows/build_win_mac.yml' - -concurrency: - group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} - cancel-in-progress: true - -jobs: - # --------------------------------------- - # Build ARM family - # --------------------------------------- - build-arm: - strategy: - fail-fast: false - matrix: - os: [windows-latest, macos-latest] - runs-on: ${{ matrix.os }} - - steps: - - name: Setup Python - uses: actions/setup-python@v5 - with: - python-version: '3.x' - - - name: Install ARM GCC - uses: carlosperate/arm-none-eabi-gcc-action@v1 - with: - release: '10.3-2021.10' - - - name: Checkout TinyUSB - uses: actions/checkout@v4 - - - name: Get Dependencies - run: | - pip install click - python3 tools/get_deps.py stm32f4 - - - name: Build - run: python3 tools/build.py -s make stm32f2 diff --git a/.github/workflows/ci_set_matrix.py b/.github/workflows/ci_set_matrix.py index 2a17be6a1..ea758d917 100644 --- a/.github/workflows/ci_set_matrix.py +++ b/.github/workflows/ci_set_matrix.py @@ -16,7 +16,7 @@ family_list = { "ch32v307 fomu gd32vf103": ["riscv-gcc"], "imxrt": ["arm-gcc", "arm-clang"], "kinetis_k kinetis_kl kinetis_k32l2": ["arm-gcc", "arm-clang"], - "lpc11 lpc13 lpc15": ["arm-gcc"], + "lpc11 lpc13 lpc15": ["arm-gcc", "arm-clang"], "lpc17 lpc18 lpc40 lpc43": ["arm-gcc", "arm-clang"], "lpc51 lpc54 lpc55": ["arm-gcc", "arm-clang"], "mcx": ["arm-gcc"], diff --git a/.github/workflows/hil_test.yml b/.github/workflows/hil_test.yml index 024ab969d..796ff32dc 100644 --- a/.github/workflows/hil_test.yml +++ b/.github/workflows/hil_test.yml @@ -24,15 +24,18 @@ on: - '.github/actions/**' - '.github/workflows/hil_test.yml' concurrency: - group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} + group: ${{ github.workflow }}-${{ github.ref }} cancel-in-progress: true jobs: + # --------------------------------------- + # Build Non Espressif + # --------------------------------------- build: if: github.repository_owner == 'hathach' runs-on: ubuntu-latest outputs: - BOARD_LIST: ${{ steps.parse_hil_json.outputs.BOARD_LIST }} + BOARDS_LIST: ${{ steps.parse_hil_json.outputs.BOARDS_LIST }} steps: - name: Checkout TinyUSB uses: actions/checkout@v4 @@ -42,38 +45,29 @@ jobs: with: python-version: '3.x' - - name: Install ARM GCC - uses: carlosperate/arm-none-eabi-gcc-action@v1 - with: - release: '12.3.Rel1' - - name: Parse HIL json id: parse_hil_json run: | sudo apt install -y jq - BOARD_LIST=$(jq -r '.boards[] | "-b " + .name' test/hil/pi4.json | tr '\n' ' ') - echo "BOARD_LIST=$BOARD_LIST" - echo >> $GITHUB_ENV "BOARD_LIST=$BOARD_LIST" - echo >> $GITHUB_OUTPUT "BOARD_LIST=$BOARD_LIST" - - name: Checkout pico-sdk for rp2040 - uses: actions/checkout@v4 + # Non-Espresif boards + BOARDS_LIST=$(jq -r '.boards[] | select(.flasher != "esptool") | "-b " + .name' test/hil/pi4.json | tr '\n' ' ') + echo "BOARDS_LIST=$BOARDS_LIST" + echo "BOARDS_LIST=$BOARDS_LIST" >> $GITHUB_ENV + echo "BOARDS_LIST=$BOARDS_LIST" >> $GITHUB_OUTPUT + + - name: Setup ARM Toolchain + uses: ./.github/actions/setup_toolchain with: - repository: raspberrypi/pico-sdk - ref: develop - path: pico-sdk + toolchain: 'arm-gcc' - name: Get Dependencies - run: | - pip install click - sudo apt install -y ninja-build - python3 tools/get_deps.py $BOARD_LIST + uses: ./.github/actions/get_deps + with: + arg: ${{ env.BOARDS_LIST }} - name: Build - run: | - python tools/build.py $BOARD_LIST - env: - PICO_SDK_PATH: ${{ github.workspace }}/pico-sdk + run: python tools/build.py $BOARDS_LIST - name: Upload Artifacts for Hardware Testing uses: actions/upload-artifact@v4 @@ -83,16 +77,71 @@ jobs: cmake-build/cmake-build-*/*/*/*.elf cmake-build/cmake-build-*/*/*/*.bin + # --------------------------------------- + # Build Espressif + # --------------------------------------- + build-esp: + runs-on: ubuntu-latest + outputs: + BOARDS_LIST: ${{ steps.parse_hil_json.outputs.BOARDS_LIST }} + steps: + - name: Checkout TinyUSB + uses: actions/checkout@v4 + + - name: Setup Python + uses: actions/setup-python@v5 + with: + python-version: '3.x' + + - name: Parse HIL json + id: parse_hil_json + run: | + sudo apt install -y jq + # Espressif boards + BOARDS_LIST=$(jq -r '.boards[] | select(.flasher == "esptool") | "-b " + .name' test/hil/pi4.json | tr '\n' ' ') + echo "BOARDS_LIST=$BOARDS_LIST" + echo "BOARDS_LIST=$BOARDS_LIST" >> $GITHUB_ENV + echo "BOARDS_LIST=$BOARDS_LIST" >> $GITHUB_OUTPUT + + - name: Setup ESP-IDF + if: env.BOARDS_LIST != '' + uses: ./.github/actions/setup_toolchain + with: + toolchain: 'esp-idf' + toolchain_url: 'v5.1.1' + + - name: Get Dependencies + uses: ./.github/actions/get_deps + with: + arg: ${{ env.BOARDS_LIST }} + + - name: Build Espressif + if: env.BOARDS_LIST != '' + run: docker run --rm -v $PWD:/project -w /project espressif/idf:v5.1.1 python3 tools/build.py $BOARDS_LIST + + - name: Upload Artifacts for Hardware Testing + uses: actions/upload-artifact@v4 + with: + name: hil_pi4_esp + path: | + cmake-build/cmake-build-*/*/*/*.bin + cmake-build/cmake-build-*/*/*/bootloader/bootloader.bin + cmake-build/cmake-build-*/*/*/partition_table/partition-table.bin + cmake-build/cmake-build-*/*/*/config.env + cmake-build/cmake-build-*/*/*/flash_args + # --------------------------------------- # Hardware in the loop (HIL) - # Current self-hosted instance is running on an RPI4. For attached hardware checkout hil_pi4.json + # Current self-hosted instance is running on an RPI4. For attached hardware checkout test/hil/pi4.json # --------------------------------------- hil-pi4: if: github.repository_owner == 'hathach' - needs: build - runs-on: [self-hosted, rp2040, nrf52840, hardware-in-the-loop] + needs: + - build + - build-esp + runs-on: [self-hosted, rp2040, nrf52840, esp32s3, hardware-in-the-loop] env: - BOARD_LIST: ${{ needs.build.outputs.BOARD_LIST }} + BOARDS_LIST: "${{ needs.build.outputs.BOARDS_LIST }} ${{ needs.build-esp.outputs.BOARDS_LIST }}" steps: - name: Clean workspace run: | @@ -103,8 +152,7 @@ jobs: # USB bus on rpi4 is not stable, reset it before testing - name: Reset USB bus run: | - lsusb - lsusb -t + # lsusb -t # reset VIA Labs 2.0 hub sudo usbreset 001/002 @@ -119,7 +167,16 @@ jobs: name: hil_pi4 path: cmake-build + - name: Download Artifacts + uses: actions/download-artifact@v4 + with: + name: hil_pi4_esp + path: cmake-build + - name: Test on actual hardware run: | - echo "BOARD_LIST=$BOARD_LIST" - python3 test/hil/hil_test.py $BOARD_LIST pi4.json + echo "BOARDS_LIST=$BOARDS_LIST" + echo "::group::{cmake-build contents}" + tree cmake-build + echo "::endgroup::" + python3 test/hil/hil_test.py $BOARDS_LIST pi4.json diff --git a/.github/workflows/pre-commit.yml b/.github/workflows/pre-commit.yml index 6b3151702..d1ffe6ca1 100644 --- a/.github/workflows/pre-commit.yml +++ b/.github/workflows/pre-commit.yml @@ -7,7 +7,7 @@ on: branches: [ master ] concurrency: - group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} + group: ${{ github.workflow }}-${{ github.ref }} cancel-in-progress: true jobs: @@ -38,7 +38,6 @@ jobs: - name: Build Fuzzer run: | - pip install click export CC=clang export CXX=clang++ fuzz_harness=$(ls -d test/fuzz/device/*/) diff --git a/examples/device/net_lwip_webserver/skip.txt b/examples/device/net_lwip_webserver/skip.txt index bb3ff7885..43cdab71a 100644 --- a/examples/device/net_lwip_webserver/skip.txt +++ b/examples/device/net_lwip_webserver/skip.txt @@ -9,6 +9,8 @@ mcu:STM32F0 mcu:KINETIS_KL family:broadcom_64bit family:broadcom_32bit +family:espressif board:curiosity_nano board:frdm_kl25z -family:espressif +# lpc55 has weird error 'ncm_interface' causes a section type conflict with 'ntb_parameters' +family:lpc55 diff --git a/examples/device/video_capture_2ch/skip.txt b/examples/device/video_capture_2ch/skip.txt index 15c176a2a..86697899b 100644 --- a/examples/device/video_capture_2ch/skip.txt +++ b/examples/device/video_capture_2ch/skip.txt @@ -12,3 +12,5 @@ board:lpcxpresso11u68 board:stm32f303disco board:stm32l412nucleo board:ek_tm4c123gxl +board:uno_r4 +board:ra4m1_ek diff --git a/examples/host/cdc_msc_hid_freertos/only.txt b/examples/host/cdc_msc_hid_freertos/only.txt index 81d993ffa..1e0e60075 100644 --- a/examples/host/cdc_msc_hid_freertos/only.txt +++ b/examples/host/cdc_msc_hid_freertos/only.txt @@ -8,5 +8,4 @@ mcu:MIMXRT10XX mcu:MIMXRT11XX mcu:MSP432E4 mcu:RX65X -mcu:RAXXX mcu:MAX3421 diff --git a/hw/bsp/lpc17/family.mk b/hw/bsp/lpc17/family.mk index 84ed95648..d719a47b7 100644 --- a/hw/bsp/lpc17/family.mk +++ b/hw/bsp/lpc17/family.mk @@ -22,8 +22,8 @@ LDFLAGS_GCC += --specs=nosys.specs --specs=nano.specs SRC_C += \ src/portable/nxp/lpc17_40/dcd_lpc17_40.c \ - src/portable/ohci/ohci.c \ src/portable/nxp/lpc17_40/hcd_lpc17_40.c \ + src/portable/ohci/ohci.c \ $(MCU_DIR)/../gcc/cr_startup_lpc175x_6x.c \ $(MCU_DIR)/src/chip_17xx_40xx.c \ $(MCU_DIR)/src/clock_17xx_40xx.c \ diff --git a/hw/bsp/lpc40/family.mk b/hw/bsp/lpc40/family.mk index 79d868f35..ef9fe57b2 100644 --- a/hw/bsp/lpc40/family.mk +++ b/hw/bsp/lpc40/family.mk @@ -20,6 +20,8 @@ LDFLAGS_GCC += --specs=nosys.specs --specs=nano.specs # All source paths should be relative to the top level. SRC_C += \ src/portable/nxp/lpc17_40/dcd_lpc17_40.c \ + src/portable/nxp/lpc17_40/hcd_lpc17_40.c \ + src/portable/ohci/ohci.c \ $(MCU_DIR)/../gcc/cr_startup_lpc40xx.c \ $(MCU_DIR)/src/chip_17xx_40xx.c \ $(MCU_DIR)/src/clock_17xx_40xx.c \ diff --git a/src/class/net/ncm_device.c b/src/class/net/ncm_device.c index 4b237e4cf..64aba011a 100644 --- a/src/class/net/ncm_device.c +++ b/src/class/net/ncm_device.c @@ -112,7 +112,7 @@ typedef struct { bool notification_xmit_is_running; // notification is currently transmitted } ncm_interface_t; -CFG_TUSB_MEM_SECTION CFG_TUSB_MEM_ALIGN tu_static ncm_interface_t ncm_interface; +CFG_TUD_MEM_SECTION CFG_TUD_MEM_ALIGN tu_static ncm_interface_t ncm_interface; /** * This is the NTB parameter structure @@ -120,7 +120,7 @@ CFG_TUSB_MEM_SECTION CFG_TUSB_MEM_ALIGN tu_static ncm_interface_t ncm_interface; * \attention * We are lucky, that byte order is correct */ -CFG_TUSB_MEM_SECTION CFG_TUSB_MEM_ALIGN tu_static const ntb_parameters_t ntb_parameters = { +CFG_TUD_MEM_SECTION CFG_TUD_MEM_ALIGN tu_static const ntb_parameters_t ntb_parameters = { .wLength = sizeof(ntb_parameters_t), .bmNtbFormatsSupported = 0x01,// 16-bit NTB supported .dwNtbInMaxSize = CFG_TUD_NCM_IN_NTB_MAX_SIZE, @@ -285,7 +285,7 @@ static xmit_ntb_t *xmit_get_next_ready_ntb(void) { * This must be called from netd_xfer_cb() so that ep_in is ready */ static bool xmit_insert_required_zlp(uint8_t rhport, uint32_t xferred_bytes) { - TU_LOG_DRV("xmit_insert_required_zlp(%d,%d)\n", rhport, xferred_bytes); + TU_LOG_DRV("xmit_insert_required_zlp(%d,%ld)\n", rhport, xferred_bytes); if (xferred_bytes == 0 || xferred_bytes % CFG_TUD_NET_ENDPOINT_SIZE != 0) { return false; @@ -521,11 +521,11 @@ static bool recv_validate_datagram(const recv_ntb_t *ntb, uint32_t len) { return false; } if (len < sizeof(nth16_t) + sizeof(ndp16_t) + 2 * sizeof(ndp16_datagram_t)) { - TU_LOG_DRV("(EE) ill min len: %d\n", len); + TU_LOG_DRV("(EE) ill min len: %lu\n", len); return false; } if (nth16->wBlockLength > len) { - TU_LOG_DRV("(EE) ill block length: %d > %d\n", nth16->wBlockLength, len); + TU_LOG_DRV("(EE) ill block length: %d > %lu\n", nth16->wBlockLength, len); return false; } if (nth16->wBlockLength > CFG_TUD_NCM_OUT_NTB_MAX_SIZE) { @@ -533,7 +533,7 @@ static bool recv_validate_datagram(const recv_ntb_t *ntb, uint32_t len) { return false; } if (nth16->wNdpIndex < sizeof(nth16) || nth16->wNdpIndex > len - (sizeof(ndp16_t) + 2 * sizeof(ndp16_datagram_t))) { - TU_LOG_DRV("(EE) ill position of first ndp: %d (%d)\n", nth16->wNdpIndex, len); + TU_LOG_DRV("(EE) ill position of first ndp: %d (%lu)\n", nth16->wNdpIndex, len); return false; } @@ -567,11 +567,11 @@ static bool recv_validate_datagram(const recv_ntb_t *ntb, uint32_t len) { while (ndp16_datagram[ndx].wDatagramIndex != 0 && ndp16_datagram[ndx].wDatagramLength != 0) { TU_LOG_DRV(" << %d %d\n", ndp16_datagram[ndx].wDatagramIndex, ndp16_datagram[ndx].wDatagramLength); if (ndp16_datagram[ndx].wDatagramIndex > len) { - TU_LOG_DRV("(EE) ill start of datagram[%d]: %d (%d)\n", ndx, ndp16_datagram[ndx].wDatagramIndex, len); + TU_LOG_DRV("(EE) ill start of datagram[%d]: %d (%lu)\n", ndx, ndp16_datagram[ndx].wDatagramIndex, len); return false; } if (ndp16_datagram[ndx].wDatagramIndex + ndp16_datagram[ndx].wDatagramLength > len) { - TU_LOG_DRV("(EE) ill end of datagram[%d]: %d (%d)\n", ndx, ndp16_datagram[ndx].wDatagramIndex + ndp16_datagram[ndx].wDatagramLength, len); + TU_LOG_DRV("(EE) ill end of datagram[%d]: %d (%lu)\n", ndx, ndp16_datagram[ndx].wDatagramIndex + ndp16_datagram[ndx].wDatagramLength, len); return false; } ++ndx; diff --git a/test/hil/hil_test.py b/test/hil/hil_test.py index dffb81765..c2699cc6f 100644 --- a/test/hil/hil_test.py +++ b/test/hil/hil_test.py @@ -25,10 +25,10 @@ # ACTION=="add", SUBSYSTEM=="tty", SUBSYSTEMS=="usb", MODE="0666", PROGRAM="/bin/sh -c 'echo $$ID_SERIAL_SHORT | rev | cut -c -8 | rev'", SYMLINK+="ttyUSB_%c.%s{bInterfaceNumber}" # ACTION=="add", SUBSYSTEM=="block", SUBSYSTEMS=="usb", ENV{ID_FS_USAGE}=="filesystem", MODE="0666", PROGRAM="/bin/sh -c 'echo $$ID_SERIAL_SHORT | rev | cut -c -8 | rev'", RUN{program}+="/usr/bin/systemd-mount --no-block --automount=yes --collect $devnode /media/blkUSB_%c.%s{bInterfaceNumber}" +import argparse import os import sys import time -import click import serial import subprocess import json @@ -318,13 +318,18 @@ def test_hid_composite_freertos(id): # ------------------------------------------------------------- # Main # ------------------------------------------------------------- -@click.command() -@click.argument('config_file') -@click.option('-b', '--board', multiple=True, default=None, help='Boards to test, all if not specified') -def main(config_file, board): +def main(): """ Hardware test on specified boards """ + parser = argparse.ArgumentParser() + parser.add_argument('config_file', help='Configuration JSON file') + parser.add_argument('-b', '--board', action='append', default=[], help='Boards to test, all if not specified') + args = parser.parse_args() + + config_file = args.config_file + boards = args.board + config_file = os.path.join(os.path.dirname(__file__), config_file) with open(config_file) as f: config = json.load(f) @@ -334,10 +339,10 @@ def main(config_file, board): 'cdc_dual_ports', 'cdc_msc', 'dfu', 'dfu_runtime', 'hid_boot_interface', ] - if len(board) == 0: + if len(boards) == 0: config_boards = config['boards'] else: - config_boards = [e for e in config['boards'] if e['name'] in board] + config_boards = [e for e in config['boards'] if e['name'] in boards] for item in config_boards: name = item['name'] diff --git a/test/hil/pi4.json b/test/hil/pi4.json index 04329bb64..bdb8a5fa5 100644 --- a/test/hil/pi4.json +++ b/test/hil/pi4.json @@ -22,6 +22,16 @@ "flasher_product": "ItsyBitsy M4 Express", "flasher_reset_pin": "2", "flasher_args": "--offset 0x4000" + }, + { + "name": "espressif_s3_devkitm", + "uid": "84F703C084E4", + "tests": [ + "cdc_msc_freertos", "hid_composite_freertos" + ], + "flasher": "esptool", + "flasher_sn": "3ea619acd1cdeb11a0a0b806e93fd3f1", + "flasher_args": "-b 1500000" } ] } diff --git a/test/hil/pi4_esp32.json b/test/hil/pi4_esp32.json deleted file mode 100644 index c95dd2d4e..000000000 --- a/test/hil/pi4_esp32.json +++ /dev/null @@ -1,14 +0,0 @@ -{ - "boards": [ - { - "name": "espressif_s3_devkitm", - "uid": "84F703C084E4", - "tests": [ - "cdc_msc_freertos", "hid_composite_freertos" - ], - "flasher": "esptool", - "flasher_sn": "3ea619acd1cdeb11a0a0b806e93fd3f1", - "flasher_args": "-b 1500000" - } - ] -} diff --git a/tools/build.py b/tools/build.py index 884cd56f4..967f7c95e 100644 --- a/tools/build.py +++ b/tools/build.py @@ -1,8 +1,8 @@ +import argparse import os import sys import time import subprocess -import click from pathlib import Path from multiprocessing import Pool @@ -125,13 +125,20 @@ def build_family(family, toolchain, build_system): return ret -@click.command() -@click.argument('families', nargs=-1, required=False) -@click.option('-b', '--board', multiple=True, default=None, help='Boards to build') -@click.option('-t', '--toolchain', default='gcc', help='Toolchain to use, default is gcc') -@click.option('-s', '--build-system', default='cmake', help='Build system to use, default is cmake') -def main(families, board, toolchain, build_system): - if len(families) == 0 and len(board) == 0: +def main(): + parser = argparse.ArgumentParser() + parser.add_argument('families', nargs='*', default=[], help='Families to build') + parser.add_argument('-b', '--board', action='append', default=[], help='Boards to build') + parser.add_argument('-t', '--toolchain', default='gcc', help='Toolchain to use, default is gcc') + parser.add_argument('-s', '--build-system', default='cmake', help='Build system to use, default is cmake') + args = parser.parse_args() + + families = args.families + boards = args.board + toolchain = args.toolchain + build_system = args.build_system + + if len(families) == 0 and len(boards) == 0: print("Please specify families or board to build") return 1 @@ -159,12 +166,23 @@ def main(families, board, toolchain, build_system): total_result[2] += fret[2] # build board (only cmake) - if board is not None: - for b in board: - r = build_board_cmake(b, toolchain) - total_result[0] += r[0] - total_result[1] += r[1] - total_result[2] += r[2] + if boards is not None: + for b in boards: + if build_system == 'cmake': + r = build_board_cmake(b, toolchain) + total_result[0] += r[0] + total_result[1] += r[1] + total_result[2] += r[2] + elif build_system == 'make': + all_examples = get_examples(find_family(b)) + with Pool(processes=os.cpu_count()) as pool: + pool_args = list((map(lambda e, bb=b, o=f"TOOLCHAIN={toolchain}": [e, bb, o], all_examples))) + r = pool.starmap(build_utils.build_example, pool_args) + # sum all element of same index (column sum) + rsum = list(map(sum, list(zip(*r)))) + total_result[0] += rsum[0] + total_result[1] += rsum[1] + total_result[2] += rsum[2] total_time = time.monotonic() - total_time print(build_separator) diff --git a/tools/build_esp32.py b/tools/build_esp32.py deleted file mode 100644 index 951467c23..000000000 --- a/tools/build_esp32.py +++ /dev/null @@ -1,106 +0,0 @@ -import os -import glob -import sys -import subprocess -import time - -import build_utils - -SUCCEEDED = "\033[32msucceeded\033[0m" -FAILED = "\033[31mfailed\033[0m" -SKIPPED = "\033[33mskipped\033[0m" - -success_count = 0 -fail_count = 0 -skip_count = 0 -exit_status = 0 - -total_time = time.monotonic() - -build_format = '| {:30} | {:30} | {:18} | {:7} | {:6} | {:6} |' -build_separator = '-' * 107 - -def filter_with_input(mylist): - if len(sys.argv) > 1: - input_args = list(set(mylist).intersection(sys.argv)) - if len(input_args) > 0: - mylist[:] = input_args - - -# Build all examples if not specified -all_examples = [entry.replace('examples/', '') for entry in glob.glob("examples/*/*_freertos")] -filter_with_input(all_examples) -all_examples.append('device/board_test') -all_examples.sort() - -# Build all boards if not specified -all_boards = [] -for entry in os.scandir("hw/bsp/espressif/boards"): - if entry.is_dir(): - all_boards.append(entry.name) -filter_with_input(all_boards) -all_boards.sort() - -def build_board(example, board): - global success_count, fail_count, skip_count, exit_status - start_time = time.monotonic() - - # Check if board is skipped - build_dir = f"cmake-build/cmake-build-{board}/{example}" - - # Generate and build - r = subprocess.run(f"cmake examples/{example} -B {build_dir} -G \"Ninja\" -DBOARD={board} -DMAX3421_HOST=1", - shell=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT) - if r.returncode == 0: - r = subprocess.run(f"cmake --build {build_dir}", shell=True, stdout=subprocess.PIPE, - stderr=subprocess.STDOUT) - build_duration = time.monotonic() - start_time - flash_size = "-" - sram_size = "-" - - if r.returncode == 0: - success = SUCCEEDED - success_count += 1 - #(flash_size, sram_size) = build_size(example, board) - else: - exit_status = r.returncode - success = FAILED - fail_count += 1 - - title = build_format.format(example, board, success, "{:.2f}s".format(build_duration), flash_size, sram_size) - if os.getenv('CI'): - # always print build output if in CI - print(f"::group::{title}") - print(r.stdout.decode("utf-8")) - print(f"::endgroup::") - else: - # print build output if failed - print(title) - if r.returncode != 0: - print(r.stdout.decode("utf-8")) - - -def build_size(example, board): - #elf_file = 'examples/device/{}/_build/{}/{}-firmware.elf'.format(example, board, board) - elf_file = 'examples/device/{}/_build/{}/*.elf'.format(example, board) - size_output = subprocess.run('size {}'.format(elf_file), shell=True, stdout=subprocess.PIPE).stdout.decode("utf-8") - size_list = size_output.split('\n')[1].split('\t') - flash_size = int(size_list[0]) - sram_size = int(size_list[1]) + int(size_list[2]) - return (flash_size, sram_size) - - -print(build_separator) -print(build_format.format('Example', 'Board', '\033[39mResult\033[0m', 'Time', 'Flash', 'SRAM')) -print(build_separator) - -for example in all_examples: - for board in all_boards: - build_board(example, board) - -total_time = time.monotonic() - total_time -print(build_separator) -print("Build Summary: {} {}, {} {}, {} {} and took {:.2f}s".format(success_count, SUCCEEDED, fail_count, FAILED, skip_count, SKIPPED, total_time)) -print(build_separator) - -sys.exit(exit_status) diff --git a/tools/get_deps.py b/tools/get_deps.py index 2359b4bd0..20cbe64c7 100644 --- a/tools/get_deps.py +++ b/tools/get_deps.py @@ -245,11 +245,10 @@ def main(): args = parser.parse_args() families = args.families - board = args.board + boards = args.board - if len(families) == 0 and len(board) == 0: - print("Please specify family or board to fetch") - return + if len(families) == 0 and len(boards) == 0: + print("Warning: family and board are not specified, only fetching mandatory dependencies.") status = 0 deps = list(deps_mandatory.keys()) @@ -258,8 +257,8 @@ def main(): deps += deps_optional.keys() else: families = list(families) - if board is not None: - for b in board: + if boards is not None: + for b in boards: f = find_family(b) if f is not None: families.append(f) -- cgit v1.3.1